Adding script for building Email app without exchange.

remove-exchange-support.sh makes it possible to build the email app without
exchange support.

This script:
- removes all packages under com.android.exchange.
- removes all lines surrounded by EXCHANGE-REMOVE-SECTION-START and
  EXCHANGE-REMOVE-SECTION-END

And the resulting source should still build and run fine.

Bug: 2369784
This commit is contained in:
Makoto Onuki 2010-02-02 15:06:52 -08:00
parent 8bb0ee3b92
commit 91237e9dcb
15 changed files with 200 additions and 38 deletions

View File

@ -18,9 +18,11 @@ include $(CLEAR_VARS)
LOCAL_MODULE_TAGS := optional
LOCAL_SRC_FILES := $(call all-java-files-under, src)
# EXCHANGE-REMOVE-SECTION-START
LOCAL_SRC_FILES += \
src/com/android/email/service/IEmailService.aidl \
src/com/android/email/service/IEmailServiceCallback.aidl
# EXCHANGE-REMOVE-SECTION-END
LOCAL_PACKAGE_NAME := Email

View File

@ -85,11 +85,13 @@
android:label="@string/account_setup_outgoing_title"
>
</activity>
<!--EXCHANGE-REMOVE-SECTION-START-->
<activity
android:name=".activity.setup.AccountSetupExchange"
android:label="@string/account_setup_exchange_title"
>
</activity>
<!--EXCHANGE-REMOVE-SECTION-END-->
<activity
android:name=".activity.setup.AccountSetupOptions"
android:label="@string/account_setup_options_title"
@ -173,6 +175,7 @@
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</activity>
<!--EXCHANGE-REMOVE-SECTION-START-->
<receiver android:name="com.android.exchange.EmailSyncAlarmReceiver"/>
<receiver android:name="com.android.exchange.MailboxAlarmReceiver"/>
<receiver android:name="com.android.exchange.BootReceiver" android:enabled="true">
@ -180,6 +183,7 @@
<action android:name="android.intent.action.BOOT_COMPLETED" />
</intent-filter>
</receiver>
<!--EXCHANGE-REMOVE-SECTION-END-->
<receiver android:name=".service.BootReceiver" android:enabled="true">
<intent-filter>
@ -222,6 +226,7 @@
>
</service>
<!--EXCHANGE-REMOVE-SECTION-START-->
<!--Required stanza to register the ContactsSyncAdapterService with SyncManager -->
<service
android:name="com.android.exchange.ContactsSyncAdapterService"
@ -282,6 +287,7 @@
android:resource="@xml/authenticator_alternate"
/>
</service>
<!--EXCHANGE-REMOVE-SECTION-END-->
<provider
android:name=".provider.AttachmentProvider"

62
remove-exchange-support.sh Executable file
View File

@ -0,0 +1,62 @@
#!/bin/bash
#
# Copyright (C) 2010 The Android Open Source Project
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
# Run this script to remove Exchange support from the Email application.
#
set -e # fail fast
# Step 0. Make sure we're in the right directory, and the user really wants it.
if [[ ! -d src/com/android/email/ ]] ; then
echo "Run the script in the root of the email source tree." 1>&2
exit 1
fi
echo ""
echo -n "Do you wish to remove exchange support from the email app? (y/N):"
read answer
if [[ "$answer" != y ]] ; then
echo "Aborted." 1>&2
exit 1
fi
# Step 1. Remove all Exchange related packages.
rm -fr src/com/android/exchange/ \
tests/src/com/android/exchange/
# Step 2. Remove lines surrounded by START-EXCHANGE and END-EXCHANGE
find . \( -name '*.java' -o -name '*.xml' -o -name 'Android.mk' \) -print0 |
xargs -0 sed -i -e '/EXCHANGE-REMOVE-SECTION-START/,/EXCHANGE-REMOVE-SECTION-END/d'
# Step 3. Remove all imports from com.android.exchange (and its subpackages).
find . -name '*.java' -print0 |
xargs -0 sed -i -e '/^import com\.android\.exchange/d'
echo ""
echo "Exchange support has been successfully removed."
exit 0

View File

@ -37,6 +37,7 @@
android:layout_height="wrap_content"
android:text="@string/debug_enable_sensitive_logging_label"
/>
<!-- EXCHANGE-REMOVE-SECTION-START -->
<CheckBox
android:id="@+id/exchange_logging"
android:layout_width="wrap_content"
@ -49,4 +50,5 @@
android:layout_height="wrap_content"
android:text="@string/debug_enable_exchange_file_logging_label"
/>
<!-- EXCHANGE-REMOVE-SECTION-END -->
</LinearLayout>

View File

@ -18,7 +18,6 @@ package com.android.email;
import com.android.email.mail.store.ExchangeStore;
import com.android.email.provider.EmailContent;
import com.android.exchange.Eas;
import android.accounts.AccountManagerFuture;
import android.content.ContentResolver;

View File

@ -23,7 +23,6 @@ import com.android.email.mail.internet.BinaryTempFileBody;
import com.android.email.provider.EmailContent;
import com.android.email.service.BootReceiver;
import com.android.email.service.MailService;
import com.android.exchange.Eas;
import android.app.Application;
import android.content.ComponentName;

View File

@ -16,6 +16,7 @@
package com.android.email;
import com.android.email.mail.MessagingException;
import com.android.email.service.EmailServiceProxy;
import com.android.email.service.IEmailService;
import com.android.email.service.IEmailServiceCallback;
@ -23,6 +24,9 @@ import com.android.exchange.SyncManager;
import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.os.IBinder;
import android.os.RemoteException;
/**
* Utility functions for Exchange support.
@ -32,7 +36,9 @@ public class ExchangeUtils {
* Starts the service for Exchange, if supported.
*/
public static void startExchangeService(Context context) {
//EXCHANGE-REMOVE-SECTION-START
context.startService(new Intent(context, SyncManager.class));
//EXCHANGE-REMOVE-SECTION-END
}
/**
@ -44,7 +50,80 @@ public class ExchangeUtils {
*/
public static IEmailService getExchangeEmailService(Context context,
IEmailServiceCallback callback) {
// TODO Return an empty IEmailService impl if exchange support is removed
return new EmailServiceProxy(context, SyncManager.class, callback);
IEmailService ret = null;
//EXCHANGE-REMOVE-SECTION-START
ret = new EmailServiceProxy(context, SyncManager.class, callback);
//EXCHANGE-REMOVE-SECTION-END
if (ret == null) {
ret = NullEmailService.INSTANCE;
}
return ret;
}
/**
* An empty {@link IEmailService} implementation which is used instead of
* {@link com.android.exchange.SyncManager} on the build with no exchange support.
*
* <p>In theory, the service in question isn't used on the no-exchange-support build,
* because we won't have any exchange accounts in that case, so we wouldn't have to have this
* class. However, there are a few places we do use the service even if there's no exchange
* accounts (e.g. setLogging), so this class is added for safety and simplicity.
*/
private static class NullEmailService implements IEmailService {
public static final NullEmailService INSTANCE = new NullEmailService();
public Bundle autoDiscover(String userName, String password) throws RemoteException {
return Bundle.EMPTY;
}
public boolean createFolder(long accountId, String name) throws RemoteException {
return false;
}
public boolean deleteFolder(long accountId, String name) throws RemoteException {
return false;
}
public void hostChanged(long accountId) throws RemoteException {
}
public void loadAttachment(long attachmentId, String destinationFile,
String contentUriString) throws RemoteException {
}
public void loadMore(long messageId) throws RemoteException {
}
public boolean renameFolder(long accountId, String oldName, String newName)
throws RemoteException {
return false;
}
public void sendMeetingResponse(long messageId, int response) throws RemoteException {
}
public void setCallback(IEmailServiceCallback cb) throws RemoteException {
}
public void setLogging(int on) throws RemoteException {
}
public void startSync(long mailboxId) throws RemoteException {
}
public void stopSync(long mailboxId) throws RemoteException {
}
public void updateFolderList(long accountId) throws RemoteException {
}
public int validate(String protocol, String host, String userName, String password,
int port, boolean ssl, boolean trustCertificates) throws RemoteException {
return MessagingException.UNSPECIFIED_EXCEPTION;
}
public IBinder asBinder() {
return null;
}
}
}

View File

@ -53,21 +53,24 @@ public class Debug extends Activity implements OnCheckedChangeListener {
mVersionView = (TextView)findViewById(R.id.version);
mEnableDebugLoggingView = (CheckBox)findViewById(R.id.debug_logging);
mEnableSensitiveLoggingView = (CheckBox)findViewById(R.id.sensitive_logging);
mEnableExchangeLoggingView = (CheckBox)findViewById(R.id.exchange_logging);
mEnableExchangeFileLoggingView = (CheckBox)findViewById(R.id.exchange_file_logging);
mEnableDebugLoggingView.setOnCheckedChangeListener(this);
mEnableSensitiveLoggingView.setOnCheckedChangeListener(this);
mEnableExchangeLoggingView.setOnCheckedChangeListener(this);
mEnableExchangeFileLoggingView.setOnCheckedChangeListener(this);
mVersionView.setText(String.format(getString(R.string.debug_version_fmt).toString(),
getString(R.string.build_number)));
mEnableDebugLoggingView.setChecked(Email.DEBUG);
mEnableSensitiveLoggingView.setChecked(Email.DEBUG_SENSITIVE);
//EXCHANGE-REMOVE-SECTION-START
mEnableExchangeLoggingView = (CheckBox)findViewById(R.id.exchange_logging);
mEnableExchangeFileLoggingView = (CheckBox)findViewById(R.id.exchange_file_logging);
mEnableExchangeLoggingView.setOnCheckedChangeListener(this);
mEnableExchangeFileLoggingView.setOnCheckedChangeListener(this);
mEnableExchangeLoggingView.setChecked(Eas.USER_LOG);
mEnableExchangeFileLoggingView.setChecked(Eas.FILE_LOG);
//EXCHANGE-REMOVE-SECTION-END
}
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
@ -80,6 +83,7 @@ public class Debug extends Activity implements OnCheckedChangeListener {
Email.DEBUG_SENSITIVE = isChecked;
mPreferences.setEnableSensitiveLogging(Email.DEBUG_SENSITIVE);
break;
//EXCHANGE-REMOVE-SECTION-START
case R.id.exchange_logging:
mPreferences.setEnableExchangeLogging(isChecked);
break;
@ -89,6 +93,7 @@ public class Debug extends Activity implements OnCheckedChangeListener {
FileLogger.close();
}
break;
//EXCHANGE-REMOVE-SECTION-END
}
updateLoggingFlags(this);
@ -115,11 +120,13 @@ public class Debug extends Activity implements OnCheckedChangeListener {
* Load enabled debug flags from the preferences and upadte the EAS debug flag.
*/
public static void updateLoggingFlags(Context context) {
//EXCHANGE-REMOVE-SECTION-START
Preferences prefs = Preferences.getPreferences(context);
int debugLogging = prefs.getEnableDebugLogging() ? Eas.DEBUG_BIT : 0;
int exchangeLogging = prefs.getEnableExchangeLogging() ? Eas.DEBUG_EXCHANGE_BIT : 0;
int fileLogging = prefs.getEnableExchangeFileLogging() ? Eas.DEBUG_FILE_BIT : 0;
int debugBits = debugLogging | exchangeLogging | fileLogging;
Controller.getInstance(context).serviceLogging(debugBits);
//EXCHANGE-REMOVE-SECTION-END
}
}

View File

@ -24,7 +24,6 @@ import com.android.email.mail.Store;
import com.android.email.provider.EmailContent.Account;
import com.android.email.provider.EmailContent.AccountColumns;
import com.android.email.provider.EmailContent.HostAuth;
import com.android.exchange.Eas;
import android.app.Activity;
import android.content.ContentResolver;

View File

@ -157,14 +157,16 @@ public class AccountSetupAccountType extends Activity implements OnClickListener
* like this.
*/
private boolean isExchangeAvailable() {
//EXCHANGE-REMOVE-SECTION-START
try {
URI uri = new URI(mAccount.getStoreUri(this));
uri = new URI("eas", uri.getUserInfo(), uri.getHost(), uri.getPort(), null, null, null);
Store.StoreInfo storeInfo = Store.StoreInfo.getStoreInfo(uri.toString(), this);
return (storeInfo != null && checkAccountInstanceLimit(storeInfo));
} catch (URISyntaxException e) {
return false;
}
//EXCHANGE-REMOVE-SECTION-END
return false;
}
/**

View File

@ -25,7 +25,6 @@ import com.android.email.mail.Store;
import com.android.email.mail.StoreSynchronizer;
import com.android.email.provider.EmailContent.Account;
import com.android.email.service.EasAuthenticatorService;
import com.android.exchange.Eas;
import android.accounts.AccountManager;
import android.accounts.AccountManagerCallback;

View File

@ -30,7 +30,6 @@ import com.android.email.provider.EmailContent.MailboxColumns;
import com.android.email.provider.EmailContent.Message;
import com.android.email.provider.EmailContent.MessageColumns;
import com.android.email.provider.EmailContent.SyncColumns;
import com.android.exchange.Eas;
import android.accounts.AccountManager;
import android.content.ContentProvider;

View File

@ -18,7 +18,6 @@ package com.android.email.service;
import com.android.email.Email;
import com.android.email.activity.setup.AccountSetupBasics;
import com.android.exchange.Eas;
import android.accounts.AbstractAccountAuthenticator;
import android.accounts.Account;

View File

@ -35,16 +35,16 @@ import java.util.HashSet;
* This is a series of unit tests for the AccountSetupAccountType class.
*/
@SmallTest
public class AccountSetupAccountTypeUnitTests
public class AccountSetupAccountTypeUnitTests
extends ActivityUnitTestCase<AccountSetupAccountType> {
// Borrowed from AccountSetupAccountType
private static final String EXTRA_ACCOUNT = "account";
Context mContext;
private HashSet<Account> mAccounts = new HashSet<Account>();
public AccountSetupAccountTypeUnitTests() {
super(AccountSetupAccountType.class);
}
@ -52,7 +52,7 @@ public class AccountSetupAccountTypeUnitTests
@Override
protected void setUp() throws Exception {
super.setUp();
mContext = this.getInstrumentation().getTargetContext();
}
@ -65,11 +65,11 @@ public class AccountSetupAccountTypeUnitTests
Uri uri = ContentUris.withAppendedId(Account.CONTENT_URI, account.mId);
mContext.getContentResolver().delete(uri, null, null);
}
// must call last because it scrubs member variables
super.tearDown();
}
/**
* Test store type limit enforcement
*/
@ -77,7 +77,7 @@ public class AccountSetupAccountTypeUnitTests
EmailContent.Account acct1 = createTestAccount("scheme1");
EmailContent.Account acct2 = createTestAccount("scheme1");
EmailContent.Account acct3 = createTestAccount("scheme2");
AccountSetupAccountType activity = startActivity(getTestIntent(acct1), null, null);
// Test with no limit
@ -85,24 +85,30 @@ public class AccountSetupAccountTypeUnitTests
info.mAccountInstanceLimit = -1;
info.mScheme = "scheme1";
assertTrue("no limit", activity.checkAccountInstanceLimit(info));
// Test with limit, but not reached
info.mAccountInstanceLimit = 3;
assertTrue("limit, but not reached", activity.checkAccountInstanceLimit(info));
// Test with limit, reached
info.mAccountInstanceLimit = 2;
assertFalse("limit, reached", activity.checkAccountInstanceLimit(info));
}
/**
* Confirm that EAS is presented (supported in this release)
* Confirm that EAS is presented, when supported.
*/
public void testEasOffered() {
Account acct1 = createTestAccount("scheme1");
AccountSetupAccountType activity = startActivity(getTestIntent(acct1), null, null);
View exchangeButton = activity.findViewById(R.id.exchange);
assertEquals(View.VISIBLE, exchangeButton.getVisibility());
int expected = View.GONE; // Default is hidden
//EXCHANGE-REMOVE-SECTION-START
expected = View.VISIBLE; // Will be visible if supported.
//EXCHANGE-REMOVE-SECTION-END
assertEquals(expected, exchangeButton.getVisibility());
}
/**
@ -115,7 +121,7 @@ public class AccountSetupAccountTypeUnitTests
mAccounts.add(account);
return account;
}
/**
* Create an intent with the Account in it
*/

View File

@ -37,17 +37,19 @@ import android.widget.EditText;
@MediumTest
public class AccountSetupExchangeTests extends
ActivityInstrumentationTestCase2<AccountSetupExchange> {
//EXCHANGE-REMOVE-SECTION-START
private AccountSetupExchange mActivity;
private EditText mServerView;
private Button mNextButton;
private CheckBox mSslRequiredCheckbox;
private CheckBox mTrustAllCertificatesCheckbox;
//EXCHANGE-REMOVE-SECTION-END
public AccountSetupExchangeTests() {
super("com.android.email", AccountSetupExchange.class);
}
//EXCHANGE-REMOVE-SECTION-START
/**
* Common setup code for all tests. Sets up a default launch intent, which some tests
* will use (others will override).
@ -62,7 +64,7 @@ public class AccountSetupExchangeTests extends
Intent i = getTestIntent("eas://user:password@server.com");
setActivityIntent(i);
}
/**
* Test processing with a complete, good URI -> good fields
*/
@ -72,7 +74,7 @@ public class AccountSetupExchangeTests extends
getActivityAndFields();
assertTrue(mNextButton.isEnabled());
}
// TODO Add tests for valid usernames in eas
// They would be <name> or <name>\<domain> or <name>/<domain> or a valid email address
@ -85,7 +87,7 @@ public class AccountSetupExchangeTests extends
getActivityAndFields();
assertFalse(mNextButton.isEnabled());
}
/**
* No password is not OK - not enabled
*/
@ -95,7 +97,7 @@ public class AccountSetupExchangeTests extends
getActivityAndFields();
assertFalse(mNextButton.isEnabled());
}
/**
* Test for non-standard but OK server names
*/
@ -103,11 +105,11 @@ public class AccountSetupExchangeTests extends
public void testGoodServerVariants() {
getActivityAndFields();
assertTrue(mNextButton.isEnabled());
mServerView.setText(" server.com ");
assertTrue(mNextButton.isEnabled());
}
/**
* Test for non-empty but non-OK server names
*/
@ -115,10 +117,10 @@ public class AccountSetupExchangeTests extends
public void testBadServerVariants() {
getActivityAndFields();
assertTrue(mNextButton.isEnabled());
mServerView.setText(" ");
assertFalse(mNextButton.isEnabled());
mServerView.setText("serv$er.com");
assertFalse(mNextButton.isEnabled());
}
@ -161,7 +163,7 @@ public class AccountSetupExchangeTests extends
/**
* TODO: Directly test validateFields() checking boolean result
*/
/**
* Get the activity (which causes it to be started, using our intent) and get the UI fields
*/
@ -173,7 +175,7 @@ public class AccountSetupExchangeTests extends
mTrustAllCertificatesCheckbox =
(CheckBox) mActivity.findViewById(R.id.account_trust_certificates);
}
/**
* Create an intent with the Account in it
*/
@ -185,5 +187,5 @@ public class AccountSetupExchangeTests extends
i.putExtra(AccountSetupExchange.EXTRA_DISABLE_AUTO_DISCOVER, true);
return i;
}
//EXCHANGE-REMOVE-SECTION-END
}