Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add Non-Admin User Support #563

Open
wants to merge 28 commits into
base: beta
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
28 commits
Select commit Hold shift + click to select a range
2476cdc
adds local server login for secondary user
arihant-confluent Jul 14, 2018
7efd84c
Add PINAccessFragment to AmahiModule
chirag-jn Jul 16, 2020
cea4805
fixes server loading issue (#378) (#379)
arihant-confluent Jun 15, 2018
f5b286c
Fix issues with PIN and server login
chirag-jn Jul 16, 2020
8c6d08c
reformat splash
chirag-jn Jul 16, 2020
95427bd
Update PIN layout
chirag-jn Jul 19, 2020
eb65aad
update strings
chirag-jn Jul 19, 2020
f673b00
hide keyboard on sign in press
chirag-jn Jul 20, 2020
3ab7a7f
update PIN layout
chirag-jn Jul 20, 2020
ff192fa
Merge branch 'nau' of https://github.com/chirag-jn/android into nau
chirag-jn Jul 26, 2020
c358c53
add log statements
chirag-jn Jul 27, 2020
c5a70d9
Merge branch 'beta' into nau
chirag-jn Jul 29, 2020
46d8afa
Merge branch 'nau' of https://github.com/chirag-jn/android into nau
chirag-jn Jul 29, 2020
465b8ae
Correct User State Issue
chirag-jn Aug 4, 2020
11a7056
Correct PIN Access Button on Login Screen
chirag-jn Aug 4, 2020
e7c453f
Change PIN Access Button to TextView
chirag-jn Aug 4, 2020
8addfba
clean code
chirag-jn Aug 4, 2020
1eacf45
Move Welcome to Amahi Server Name to Constants.java
chirag-jn Aug 4, 2020
af1d505
Add Activity Callbacks
chirag-jn Aug 21, 2020
fcc7162
Merge branch 'beta' into nau
chirag-jn Aug 23, 2020
dd9fd31
Merge commit 'refs/pull/634/head' of https://github.com/amahi/android…
chirag-jn Aug 24, 2020
ce0058f
Correct Issues with NavBar
chirag-jn Aug 24, 2020
9690eb2
remove extra log statements
chirag-jn Aug 24, 2020
be4f9fc
reformat code
chirag-jn Aug 24, 2020
261d7c5
Merge branch 'beta' into nau
chirag-jn Aug 24, 2020
4e47079
Merge branch 'beta' into nau
chirag-jn Aug 24, 2020
de208e2
Merge branch 'beta' into nau
chirag-jn Feb 27, 2021
9a03b5a
Merge branch 'beta' into nau
chirag-jn Feb 28, 2021
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@
tools:ignore="MissingLeanbackLauncher">

<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
<uses-permission android:name="android.permission.DOWNLOAD_WITHOUT_NOTIFICATION" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
Expand Down
6 changes: 4 additions & 2 deletions src/main/java/org/amahi/anywhere/AmahiModule.java
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,6 @@
import android.app.Application;
import android.content.Context;

import org.amahi.anywhere.activity.AuthenticationActivity;
import org.amahi.anywhere.activity.NativeVideoActivity;
import org.amahi.anywhere.activity.NavigationActivity;
import org.amahi.anywhere.activity.OfflineFilesActivity;
Expand All @@ -36,7 +35,9 @@
import org.amahi.anywhere.activity.WebViewActivity;
import org.amahi.anywhere.cache.CacheModule;
import org.amahi.anywhere.fragment.AudioListFragment;
import org.amahi.anywhere.fragment.MainLoginFragment;
import org.amahi.anywhere.fragment.NavigationFragment;
import org.amahi.anywhere.fragment.PINAccessFragment;
import org.amahi.anywhere.fragment.ServerAppsFragment;
import org.amahi.anywhere.fragment.ServerFileAudioFragment;
import org.amahi.anywhere.fragment.ServerFileDownloadingFragment;
Expand Down Expand Up @@ -76,7 +77,6 @@
CacheModule.class
},
injects = {
AuthenticationActivity.class,
NavigationActivity.class,
ServerAppActivity.class,
OfflineFilesActivity.class,
Expand All @@ -87,6 +87,8 @@
NativeVideoActivity.class,
RecentFilesActivity.class,
ServerFileWebActivity.class,
MainLoginFragment.class,
PINAccessFragment.class,
NavigationFragment.class,
ServerSharesFragment.class,
ServerAppsFragment.class,
Expand Down
3 changes: 3 additions & 0 deletions src/main/java/org/amahi/anywhere/account/AmahiAccount.java
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,9 @@
*/
public class AmahiAccount extends Account {
public static final String TYPE = "org.amahi";
public static final String TYPE_LOCAL = "org.amahi.local";

public static String accountType = AmahiAccount.TYPE;

public static final String TYPE_TOKEN = String.format("%s.FULL", TYPE);

Expand Down
257 changes: 78 additions & 179 deletions src/main/java/org/amahi/anywhere/activity/AuthenticationActivity.java
Original file line number Diff line number Diff line change
Expand Up @@ -21,44 +21,33 @@

import android.accounts.Account;
import android.accounts.AccountManager;
import android.app.Activity;
import android.content.Context;
import android.os.Bundle;
import android.text.Editable;
import android.text.TextWatcher;
import android.text.method.LinkMovementMethod;
import android.view.View;
import android.view.inputmethod.EditorInfo;
import android.widget.EditText;
import android.widget.TextView;

import androidx.appcompat.app.AppCompatDelegate;
import androidx.fragment.app.Fragment;

import com.dd.processbutton.iml.ActionProcessButton;
import com.google.android.material.textfield.TextInputLayout;
import com.squareup.otto.Subscribe;

import org.amahi.anywhere.AmahiApplication;
import org.amahi.anywhere.R;
import org.amahi.anywhere.account.AccountAuthenticatorAppCompatActivity;
import org.amahi.anywhere.account.AmahiAccount;
import org.amahi.anywhere.bus.AuthenticationConnectionFailedEvent;
import org.amahi.anywhere.bus.AuthenticationFailedEvent;
import org.amahi.anywhere.bus.AuthenticationSucceedEvent;
import org.amahi.anywhere.bus.BusProvider;
import org.amahi.anywhere.server.client.AmahiClient;
import org.amahi.anywhere.bus.PINAccessEvent;
import org.amahi.anywhere.fragment.MainLoginFragment;
import org.amahi.anywhere.fragment.PINAccessFragment;
import org.amahi.anywhere.util.Constants;
import org.amahi.anywhere.util.Fragments;
import org.amahi.anywhere.util.LocaleHelper;
import org.amahi.anywhere.util.ViewDirector;

import javax.inject.Inject;
import org.amahi.anywhere.util.Preferences;

/**
* Authentication activity. Allows user authentication. If operation succeed
* the authentication token is saved at the {@link android.accounts.AccountManager}.
*/
public class AuthenticationActivity extends AccountAuthenticatorAppCompatActivity implements TextWatcher {
@Inject
AmahiClient amahiClient;
public class AuthenticationActivity extends AccountAuthenticatorAppCompatActivity {

@Override
protected void onCreate(Bundle savedInstanceState) {
Expand All @@ -70,183 +59,64 @@ protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_authentication);

setUpInjections();

setUpAuthentication();

}

private void setUpInjections() {
AmahiApplication.from(this).inject(this);
}

private void setUpAuthentication() {
setUpAuthenticationMessages();
setUpAuthenticationListeners();
}

private String getUsername() {
return getUsernameEdit().getText().toString();
}

private EditText getUsernameEdit() {
TextInputLayout username_layout = findViewById(R.id.username_layout);
return username_layout.getEditText();
}

private String getPassword() {
return getPasswordEdit().getText().toString();
}

private EditText getPasswordEdit() {
TextInputLayout password_layout = findViewById(R.id.password_layout);
return password_layout.getEditText();
}

private ActionProcessButton getAuthenticationButton() {
return findViewById(R.id.button_authentication);
}

private void setUpAuthenticationMessages() {
TextView forgotPassword = findViewById(R.id.text_forgot_password);
TextView authenticationConnectionFailureMessage = findViewById(R.id.text_message_authentication_connection);
forgotPassword.setMovementMethod(LinkMovementMethod.getInstance());
authenticationConnectionFailureMessage.setMovementMethod(LinkMovementMethod.getInstance());
}

private void setUpAuthenticationListeners() {
setUpAuthenticationTextListener();
setUpAuthenticationActionListener();
}

private void setUpAuthenticationTextListener() {
getUsernameEdit().addTextChangedListener(this);
getPasswordEdit().addTextChangedListener(this);
getPasswordEdit().setOnEditorActionListener((v, actionId, event) -> {
boolean handled = false;
if (actionId == EditorInfo.IME_ACTION_GO) {
onClick(getAuthenticationButton());
handled = true;
}
return handled;
});
setUpAuthenticationFragment();
}

@Override
public void onTextChanged(CharSequence text, int after, int before, int count) {
hideAuthenticationFailureMessage();
}

private void hideAuthenticationFailureMessage() {
ViewDirector.of(this, R.id.animator_message).show(R.id.view_message_empty);
protected void onRestoreInstanceState(Bundle savedInstanceState) {
super.onRestoreInstanceState(savedInstanceState);
AmahiAccount.accountType = savedInstanceState.getString(State.ACCOUNT_TYPE, AmahiAccount.TYPE);
}

@Override
public void afterTextChanged(Editable text) {
}

@Override
public void beforeTextChanged(CharSequence text, int start, int count, int before) {
}

private void setUpAuthenticationActionListener() {
getAuthenticationButton().setOnClickListener(this::onClick);
}

public void onClick(View view) {
if (getUsername().trim().isEmpty() || getPassword().trim().isEmpty()) {
ViewDirector.of(this, R.id.animator_message).show(R.id.text_message_authentication_empty);

if (getUsername().trim().isEmpty())
getUsernameEdit().requestFocus();

if (getPassword().trim().isEmpty())
getPasswordEdit().requestFocus();

if (getUsername().trim().isEmpty() && getPassword().trim().isEmpty())
getUsernameEdit().requestFocus();

private void setUpAuthenticationFragment() {
if (AmahiAccount.accountType.equals(AmahiAccount.TYPE)) {
MainLoginFragment f = (MainLoginFragment) getSupportFragmentManager().findFragmentByTag(MainLoginFragment.TAG);
if (f == null) {
showMainLoginFragment();
}
} else {
startAuthentication();

authenticate();
PINAccessFragment f = (PINAccessFragment) getSupportFragmentManager().findFragmentByTag(PINAccessFragment.TAG);
if (f == null) {
showPINAccessFragment();
}
}
}

private void startAuthentication() {
hideAuthenticationText();

showProgress();

hideAuthenticationFailureMessage();
}

private void hideAuthenticationText() {
getUsernameEdit().setEnabled(false);
getPasswordEdit().setEnabled(false);
}

private void showProgress() {
ActionProcessButton authenticationButton = getAuthenticationButton();

authenticationButton.setMode(ActionProcessButton.Mode.ENDLESS);
authenticationButton.setProgress(1);
}

private void authenticate() {
amahiClient.authenticate(getUsername().trim(), getPassword());
}

@Subscribe
public void onAuthenticationFailed(AuthenticationFailedEvent event) {
finishAuthentication();

showAuthenticationFailureMessage();
}

private void finishAuthentication() {
showAuthenticationText();

hideProgress();
}

private void showAuthenticationText() {
getUsernameEdit().setEnabled(true);
getPasswordEdit().setEnabled(true);
}

private void hideProgress() {
getAuthenticationButton().setProgress(0);
}

private void showAuthenticationFailureMessage() {
ViewDirector.of(this, R.id.animator_message).show(R.id.text_message_authentication);
private void showMainLoginFragment() {
Fragment fragment = Fragments.Builder.buildMainLoginFragment();
getSupportFragmentManager()
.beginTransaction()
.replace(R.id.main_container, fragment, MainLoginFragment.TAG)
.commit();
}

@Subscribe
public void onAuthenticationConnectionFailed(AuthenticationConnectionFailedEvent event) {
finishAuthentication();

showAuthenticationConnectionFailureMessage();
}
public void onAuthenticationSucceed(AuthenticationSucceedEvent event) {
if (AmahiAccount.accountType.equals(AmahiAccount.TYPE)) {
MainLoginFragment fragment = (MainLoginFragment) getSupportFragmentManager().findFragmentByTag(MainLoginFragment.TAG);

private void showAuthenticationConnectionFailureMessage() {
ViewDirector.of(this, R.id.animator_message).show(R.id.text_message_authentication_connection);
}
finishAuthentication(event.getAuthentication().getToken(), fragment.getUsername(), fragment.getPassword());
} else {
PINAccessFragment fragment = (PINAccessFragment) getSupportFragmentManager().findFragmentByTag(PINAccessFragment.TAG);

@Subscribe
public void onAuthenticationSucceed(AuthenticationSucceedEvent event) {
finishAuthentication(event.getAuthentication().getToken());
finishAuthentication(event.getAuthentication().getToken(), Constants.pinAccessUsername, fragment.getPIN());
}
}

private void finishAuthentication(String authenticationToken) {
private void finishAuthentication(String authenticationToken, String username, String password) {
AccountManager accountManager = AccountManager.get(this);

Bundle authenticationBundle = new Bundle();

Account account = new AmahiAccount(getUsername());
Account account = new AmahiAccount(username);
if (AmahiAccount.accountType.equals(AmahiAccount.TYPE_LOCAL)) {
authenticationBundle.putString("ip", Preferences.getLocalServerIP(this));
authenticationBundle.putString("is_local", "T");
} else {
authenticationBundle.putString("is_local", "F");
}

if (accountManager.addAccountExplicitly(account, getPassword(), null)) {
if (accountManager.addAccountExplicitly(account, password, authenticationBundle)) {
authenticationBundle.putString(AccountManager.KEY_ACCOUNT_NAME, account.name);
authenticationBundle.putString(AccountManager.KEY_ACCOUNT_TYPE, account.type);
authenticationBundle.putString(AccountManager.KEY_AUTHTOKEN, authenticationToken);
Expand All @@ -256,32 +126,61 @@ private void finishAuthentication(String authenticationToken) {

setAccountAuthenticatorResult(authenticationBundle);

setResult(Activity.RESULT_OK);
setResult(RESULT_OK);

finish();
}

@Subscribe
public void onPINAccess(PINAccessEvent event) {
AmahiAccount.accountType = AmahiAccount.TYPE_LOCAL;
showPINAccessFragment();
}

private void showPINAccessFragment() {
Fragment fragment = Fragments.Builder.buildPINFragment();
getSupportFragmentManager()
.beginTransaction()
.replace(R.id.main_container, fragment, PINAccessFragment.TAG)
.addToBackStack(MainLoginFragment.TAG)
.commit();
}

@Override
protected void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);

outState.putString(State.ACCOUNT_TYPE, AmahiAccount.accountType);
}

@Override
protected void onResume() {
public void onResume() {
super.onResume();

BusProvider.getBus().register(this);
}

@Override
protected void onPause() {
public void onPause() {
super.onPause();

BusProvider.getBus().unregister(this);
}

@Override
public void onBackPressed() {
finishAffinity();
super.onBackPressed();
}

@Override
protected void attachBaseContext(Context newBase) {
super.attachBaseContext(LocaleHelper.onAttach(newBase));
}

private static final class State {
static final String ACCOUNT_TYPE = "account_type";

private State() {
}
}
}
Loading