728x90

1. 구글 계정 로그인 Api?

- OAuth 방식

2019/10/07 - [Dev/Etc] - [생활코딩] OAuth 2.0

 

- OAuth를 통해 사용자User(Resource Owner)로부터 허가를 받고 얻어낸 Access Token을 이용하여, Resource Server에서 얻어온 사용자 ID를 통해 사용자를 인증한다.

- 사용자의 허가를 받은 Access Token을 이용한 ID이므로, PW가 없어도 해당 사용자임이 증명되며 로그인 가능하다.

 

2. Android Studio 환경설정

(참고: https://developers.google.com/identity/sign-in/android/start-integrating)

 

1) Project단 build.gradle에 google()추가

allprojects {
    repositories {
        google()

        // If you're using a version of Gradle lower than 4.1, you must instead use:
        // maven {
        //     url 'https://maven.google.com'
        // }
    }
}

 

2) Module단 build.gradle에 

    'com.google.android.gms:play-services-auth:17.0.0' 추가

    (version 참고: https://developers.google.com/android/guides/setup )

 

apply plugin: 'com.android.application'
    ...

    dependencies {
        implementation 'com.google.android.gms:play-services-auth:17.0.0'
    }

 

3) Configure a Google API Console project

To configure a Google API Console project, click the button below, and specify your app's package name when prompted. You will also need to provide the SHA-1 hash of your signing certificate. See Authenticating Your Client for information.

 

 

4) Activity 코드

Configure a Google API Console project and set up your Android Studio project.

 (※코드 추가 전에 구글 Api 콘솔 프로젝트를 설정하고, 안드로이드 프로젝트를 셋업할 것)

// Configure sign-in to request the user's ID, email address, and basic
// profile. ID and basic profile are included in DEFAULT_SIGN_IN.
GoogleSignInOptions gso = new GoogleSignInOptions.Builder(GoogleSignInOptions.DEFAULT_SIGN_IN)
        .requestEmail()
        .build();

 

sign-in activity의 onCreate에 본인이 원하는 옵션을 정의한 GoogleSignInClient 객체를 생성. 

// Build a GoogleSignInClient with the options specified by gso.
mGoogleSignInClient = GoogleSignIn.getClient(this, gso);

sign-in activity의 onStart에 사용자가 구글로부터 당신의 앱에 이미 sign in했는지를 체크하도록 추가.

// Check for existing Google Sign In account, if the user is already signed in
// the GoogleSignInAccount will be non-null.
GoogleSignInAccount account = GoogleSignIn.getLastSignedInAccount(this);
updateUI(account);

추가 참고

https://github.com/googlesamples/google-services

 

 

Reference

https://github.com/googlesamples/google-services

https://developers.google.com/identity/sign-in/android

https://developers.google.com/android/guides/setup

https://galid1.tistory.com/109

 

 

 

728x90
728x90

 

For Debug mode:

 

keytool -list -v -keystore ~/.android/debug.keystore -alias androiddebugkey -storepass android -keypass android

 

for Release mode:

 

keytool -list -v -keystore {keystore_name} -alias {alias_name}

 

example:

keytool -list -v -keystore C:\Users\MG\Desktop\test.jks -alias test

 

    + Debug 모드 필요시 간단한 방법
  1. Run your project

  2. Click on Gradle menu

  3. Expand Gradle Tasks tree

  4. Double click on android -> signingReport and see the magic

  5. It will tell you everything on the Run tab

 

Result Under Run Tab If Android Studio < 2.2

From android studio 2.2
Result will be available under Run console but use highlighted toggle button

 

 

Reference

https://stackoverflow.com/questions/15727912/sha-1-fingerprint-of-keystore-certificate

 

 

 

728x90
728x90

 

1. Room 라이브러리란?

- AAC(Android Architecture Component) 중 하나.

- SQLite DB를 보다 쉽게 사용할 수 있도록 하는 구글의 새로운 ORM(Object Relational Mapping)

 

(*ORM: DB 테이블과 매핑되는 객체를 만들고 그 객체에서 DB를 관리하는 프로그램)

 

 

https://developer.android.com/jetpack/androidx/releases/room

 

Room  |  Android Developers

The Room persistence library provides an abstraction layer over SQLite to allow for more robust database access while harnessing the full power of SQLite. Latest Update Current Stable Release Next Release Candidate Beta Release Alpha Release October 9, 201

developer.android.com

 

2. build.gradle (app) dependencies 추가

    dependencies {
      def room_version = "2.2.0-beta01"

      implementation "androidx.room:room-runtime:$room_version"
      
      // For Kotlin use kapt instead of annotationProcessor
      annotationProcessor "androidx.room:room-compiler:$room_version" 

      // optional - Kotlin Extensions and Coroutines support for Room
      implementation "androidx.room:room-ktx:$room_version"

      // optional - RxJava support for Room
      implementation "androidx.room:room-rxjava2:$room_version"

      // optional - Guava support for Room, including Optional and ListenableFuture
      implementation "androidx.room:room-guava:$room_version"

      // Test helpers
      testImplementation "androidx.room:room-testing:$room_version"
    }
    

참고: Kotlin 기반 앱의 경우 annotationProcessor 대신 kapt를 사용해야 합니다. 또한 kotlin-kapt 플러그인을 추가해야 합니다.

 

 

3. 개념

- Entity: DB에 저장할 데이터의 형식을 정의. 즉, DB의 테이블.

- DAO(Data Access Object): 데이터접근 객체, 즉 데이터베이스를 통해 수행할 작업(CRUD)을 함수로 정의한 클래스. DAO는 interface나 abstract class가 되야 함. 만약 abstract class로 만들면, 선택적으로 RoomDatabase객체를 생성자의 매개변수로 가질수 있으며 Room은 각 DAO의 구현을 컴파일 시간에 생성함.

- Room Database: DB를 생성하거나 버전을 관리하는 Room DB 객체. 해당 객체를 생성하는 비용이 많이 들기 때문에, 프로젝트에서 singleton으로 구현해야함.

 

 

 

 

4. 주의사항

- Room의 데이터는 모두 Background-Thread에서 처리해야함. 즉, Main-Thread에서의 DB접근을 허용하지 않음. 허용하고 싶다면 데이터베이스를 생성하는 빌더에서 allowMainThreadQueries()를 호출해야함.

- 허용하지 않는 이유는 데이터를 받아오는 작업이 길어질 경우 UI가 장시간 멈춰버릴수 있기 때문. 그래서 보통 비동기 쿼리를 하게 되는데 반환값으로는 LiveData 또는 RxJava의 Flowable으로 사용하는 경우가 많음.

 

 

5. 자세한 사용 예시

1) User라는 Entity 테이블을 만들 경우,

1
2
3
4
5
6
7
8
9
10
11
@Entity(tableName = "users")
public class User {
    @PrimaryKey
    public int uid;
 
    @ColumnInfo(name = "first_name")
    public String firstName;
 
    @ColumnInfo(name = "last_name")
    public String lastName;
}
cs

@Entity : 테이블로 사용할 클래스를 지정하는 annotation. 기본적으로 Room은 클래스이름을 데이터베이스의 테이블명으로 사용함.

             그러나 만약에 다른 이름을 쓰고 싶다면 @Entity annotation에 tableName속성을 지정하면 됨

             (ex. @Entity(tableName = "users")

 

@PrimaryKey : PK에 적용

@ColumnInfo : 앞서 설명한 테이블명처럼, 필드명을 별도로 지정하고 싶을 경우 사용하는 annotation. 지정하고싶지 않을 경우에는 생략 가능.

 

 

2) UserDao라는 DAO를 만들 경우,

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
@Dao
public interface UserDao {
    @Query("SELECT * FROM user")
    List<User> getAll();
 
    @Query("SELECT * FROM user WHERE uid IN (:userIds)")
    List<User> loadAllByIds(int[] userIds);
 
    @Query("SELECT * FROM user WHERE first_name LIKE :first AND " +
           "last_name LIKE :last LIMIT 1")
    User findByName(String first, String last);
 
    @Insert
    void insertAll(User... users);
 
    @Delete
    void delete(User user);
 
    @Update
    void updateUsers(User... users);
 
}
cs

 

@Dao : CRUD 작업을 정의할 interface를 지정하는 annotation

@Query: 컴파일 시간에 알맞은 쿼리인지를 입증하게 되고, 문제가 있을 시에는 컴파일 에러가 발생함. 

Room은 또한 쿼리에 대한 반환값을 확인함.. 반환되는 객체의 필드의 이름이 만약에 대응되는 컬럼이름이 질의응답에서 일치하지 않는다면 Room은 다음과 같이 두가지 방법중 하나로 알림을 줌.
        (1) 몇몇의 필드명만 일치하는 경우에는 경고 발생
        (2) 일치하지 않는 필드명이 있을시 에러 발생

 

+ 이미 저장된 객체가 있을 경우에는 아래와 같이 덮어쓰기도 가능.

1
2
3
4
5
6
@Dao
public interface UserDao {
    @Insert(onConflict = OnConflictStrategy.REPLACE)
    void insert(Person person)
}
 
cs

 

- Room DB 객체

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
@Database(entities = {User.class}, version = 1)
public abstract class AppDatabase extends RoomDatabase {
    public abstract UserDao userDao();
 
    //Room Database Singleton
    private static AppDatabase INSTANCE;
 
    private static final Object sLock = new Object();
 
    public static AppDatabase getInstance(Context context) {
        synchronized (sLock) {
            if(INSTANCE==null) {
                INSTANCE=Room.databaseBuilder(context.getApplicationContext(),
                        AppDatabase.class"Users.db"//Users.db == database-name
                        .build();
            }
            return INSTANCE;
        }
    }
}
cs

 

 

보다 자세히 잘 나와있는 예시

https://codelabs.developers.google.com/codelabs/android-room-with-a-view/#0

 

Android Room with a View - Java

When data changes you usually want to take some action, such as displaying the updated data in the UI. This means you have to observe the data so that when it changes, you can react. Depending on how the data is stored, this can be tricky. Observing change

codelabs.developers.google.com

 

 

Reference

https://black-jin0427.tistory.com/53

https://www.charlezz.com/?p=368

https://developer.android.com/training/data-storage/room/#java

 

 

728x90
728x90

 

해당현상

 

 

해결책: Manifest.xml의 <intent-filter> 사이에 아래의 코드 추가

<action android:name="android.intent.action.VIEW" />

 

<예시>

- 기존

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
 <application
        android:name="경로.MyApp"
        android:allowBackup="true"
        android:hardwareAccelerated="true"
        android:icon="@drawable/icon"
        android:label="@string/app_name"
        android:largeHeap="true">
        <activity
            android:name="경로.LogInActivity"
            android:label="@string/app_name"
            android:screenOrientation="portrait"
            android:theme="@style/AppTheme.NoActionBar"
            android:windowSoftInputMode="stateHidden">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
 
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
</application>
cs

 

 

- 변경

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
 <application
        android:name="경로.MyApp"
        android:allowBackup="true"
        android:hardwareAccelerated="true"
        android:icon="@drawable/icon"
        android:label="@string/app_name"
        android:largeHeap="true">
        <activity
            android:name="경로.LogInActivity"
            android:label="@string/app_name"
            android:screenOrientation="portrait"
            android:theme="@style/AppTheme.NoActionBar"
            android:windowSoftInputMode="stateHidden">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <action android:name="android.intent.action.VIEW" />
 
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
</application>
cs

 

 

 

Reference

https://stackoverflow.com/questions/34367875/android-adding-at-least-one-activity-with-an-action-view-intent-filter-after-u

728x90

+ Recent posts