1 /* 2 * Copyright (C) 2008 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.mms.ui; 18 19 import java.io.FileInputStream; 20 import java.util.ArrayList; 21 import java.util.Random; 22 23 import com.android.mms.R; 24 import com.android.mms.ui.ComposeMessageActivity; 25 import com.android.mms.ui.MessageListView; 26 27 import android.content.Intent; 28 import android.graphics.drawable.Drawable; 29 import android.test.ActivityInstrumentationTestCase2; 30 import android.test.suitebuilder.annotation.LargeTest; 31 import android.util.Log; 32 import android.view.MenuItem; 33 import android.view.SubMenu; 34 import android.view.View; 35 import android.view.ContextMenu.ContextMenuInfo; 36 import android.widget.EditText; 37 import android.widget.TextView; 38 import android.widget.Button; 39 40 /** 41 * Test threads with thousands of messages 42 * NOTE: you first have to put the unix words file on the device: 43 * example: adb push ~/words /data/data/com.android.mms/files 44 * and then push a file that contains a comma separated list of numbers to send to. 45 * example: adb push ~/recipients /data/data/com.android.mms/files 46 * 47 */ 48 public class LongThreadTest 49 extends ActivityInstrumentationTestCase2<ComposeMessageActivity> { 50 51 private TextView mRecipientsView; 52 private EditText mTextEditor; 53 private EditText mSubjectTextEditor; // Text editor for MMS subject 54 static final String TAG = "LongThreadTest"; 55 private ArrayList<String> mWords; 56 private ArrayList<String> mRecipients; 57 private int mWordCount; 58 private Random mRandom = new Random(); 59 60 public LongThreadTest() { 61 super("com.android.mms", ComposeMessageActivity.class); 62 } 63 64 @Override 65 protected void setUp() throws Exception { 66 super.setUp(); 67 68 ComposeMessageActivity a = getActivity(); 69 mRecipientsView = (TextView)a.findViewById(R.id.recipients_editor); 70 mTextEditor = (EditText)a.findViewById(R.id.embedded_text_editor); 71 mSubjectTextEditor = (EditText)a.findViewById(R.id.subject); 72 73 // Read in dictionary of words 74 mWords = new ArrayList<String>(98568); // count of words in words file 75 StringBuilder sb = new StringBuilder(); 76 try { 77 Log.v(TAG, "Loading dictionary of words"); 78 FileInputStream words = a.openFileInput("words"); 79 int c; 80 while ((c = words.read()) != -1) { 81 if (c == '\r' || c == '\n') { 82 String word = sb.toString().trim(); 83 if (word.length() > 0) { 84 mWords.add(word); 85 } 86 sb.setLength(0); 87 } else { 88 sb.append((char)c); 89 } 90 } 91 words.close(); 92 mWordCount = mWords.size(); 93 Log.v(TAG, "Loaded dictionary word count: " + mWordCount); 94 } catch (Exception e) { 95 Log.e(TAG, "can't open words file at /data/data/com.android.mms/files/words"); 96 return; 97 } 98 99 // Read in list of recipients 100 mRecipients = new ArrayList<String>(); 101 try { 102 Log.v(TAG, "Loading recipients"); 103 FileInputStream recipients = a.openFileInput("recipients"); 104 int c; 105 while ((c = recipients.read()) != -1) { 106 if (c == '\r' || c == '\n' || c == ',') { 107 String recipient = sb.toString().trim(); 108 if (recipient.length() > 0) { 109 mRecipients.add(recipient); 110 } 111 sb.setLength(0); 112 } else { 113 sb.append((char)c); 114 } 115 } 116 recipients.close(); 117 Log.v(TAG, "Loaded recipients: " + mRecipients.size()); 118 } catch (Exception e) { 119 Log.e(TAG, "can't open recipients file at /data/data/com.android.mms/files/recipients"); 120 return; 121 } 122 } 123 124 private String generateMessage() { 125 int wordsInMessage = mRandom.nextInt(9) + 1; // up to 10 words in the message 126 StringBuilder msg = new StringBuilder(); 127 for (int i = 0; i < wordsInMessage; i++) { 128 msg.append(mWords.get(mRandom.nextInt(mWordCount)) + " "); 129 } 130 return msg.toString(); 131 } 132 133 private class AddSubjectMenuItem implements MenuItem { 134 private static final int MENU_ADD_SUBJECT = 0; 135 136 public char getAlphabeticShortcut() { 137 // TODO Auto-generated method stub 138 return 0; 139 } 140 141 public int getGroupId() { 142 // TODO Auto-generated method stub 143 return 0; 144 } 145 146 public Drawable getIcon() { 147 // TODO Auto-generated method stub 148 return null; 149 } 150 151 public Intent getIntent() { 152 // TODO Auto-generated method stub 153 return null; 154 } 155 156 public int getItemId() { 157 return MENU_ADD_SUBJECT; 158 } 159 160 public ContextMenuInfo getMenuInfo() { 161 // TODO Auto-generated method stub 162 return null; 163 } 164 165 public char getNumericShortcut() { 166 // TODO Auto-generated method stub 167 return 0; 168 } 169 170 public int getOrder() { 171 // TODO Auto-generated method stub 172 return 0; 173 } 174 175 public SubMenu getSubMenu() { 176 // TODO Auto-generated method stub 177 return null; 178 } 179 180 public CharSequence getTitle() { 181 // TODO Auto-generated method stub 182 return null; 183 } 184 185 public CharSequence getTitleCondensed() { 186 // TODO Auto-generated method stub 187 return null; 188 } 189 190 public boolean hasSubMenu() { 191 // TODO Auto-generated method stub 192 return false; 193 } 194 195 public boolean isCheckable() { 196 // TODO Auto-generated method stub 197 return false; 198 } 199 200 public boolean isChecked() { 201 // TODO Auto-generated method stub 202 return false; 203 } 204 205 public boolean isEnabled() { 206 // TODO Auto-generated method stub 207 return false; 208 } 209 210 public boolean isVisible() { 211 // TODO Auto-generated method stub 212 return false; 213 } 214 215 public MenuItem setAlphabeticShortcut(char alphaChar) { 216 // TODO Auto-generated method stub 217 return null; 218 } 219 220 public MenuItem setCheckable(boolean checkable) { 221 // TODO Auto-generated method stub 222 return null; 223 } 224 225 public MenuItem setChecked(boolean checked) { 226 // TODO Auto-generated method stub 227 return null; 228 } 229 230 public MenuItem setEnabled(boolean enabled) { 231 // TODO Auto-generated method stub 232 return null; 233 } 234 235 public MenuItem setIcon(Drawable icon) { 236 // TODO Auto-generated method stub 237 return null; 238 } 239 240 public MenuItem setIcon(int iconRes) { 241 // TODO Auto-generated method stub 242 return null; 243 } 244 245 public MenuItem setIntent(Intent intent) { 246 // TODO Auto-generated method stub 247 return null; 248 } 249 250 public MenuItem setNumericShortcut(char numericChar) { 251 // TODO Auto-generated method stub 252 return null; 253 } 254 255 public MenuItem setOnMenuItemClickListener( 256 OnMenuItemClickListener menuItemClickListener) { 257 // TODO Auto-generated method stub 258 return null; 259 } 260 261 public MenuItem setShortcut(char numericChar, char alphaChar) { 262 // TODO Auto-generated method stub 263 return null; 264 } 265 266 public MenuItem setTitle(CharSequence title) { 267 // TODO Auto-generated method stub 268 return null; 269 } 270 271 public MenuItem setTitle(int title) { 272 // TODO Auto-generated method stub 273 return null; 274 } 275 276 public MenuItem setTitleCondensed(CharSequence title) { 277 // TODO Auto-generated method stub 278 return null; 279 } 280 281 public MenuItem setVisible(boolean visible) { 282 // TODO Auto-generated method stub 283 return null; 284 } 285 286 } 287 288 private abstract class MessageRunnable implements Runnable { 289 protected String mRecipient; 290 291 public void setRecipient(String recipient) { 292 mRecipient = recipient; 293 } 294 } 295 296 private MessageRunnable mSendSmsMessage = new MessageRunnable() { 297 public void run() { 298 // only on the first message will there be a recipients editor 299 if (mRecipientsView.getVisibility() == View.VISIBLE) { 300 mRecipientsView.setText(mRecipient); 301 } 302 mTextEditor.setText(generateMessage()); 303 final ComposeMessageActivity a = getActivity(); 304 Button send = (Button)a.findViewById(R.id.send_button); 305 send.performClick(); 306 } 307 }; 308 309 private MessageRunnable mSendMmsMessage = new MessageRunnable() { 310 public void run() { 311 // only on the first message will there be a recipients editor 312 if (mRecipientsView.getVisibility() == View.VISIBLE) { 313 mRecipientsView.setText(mRecipient); 314 } 315 // Add a subject 316 final ComposeMessageActivity a = getActivity(); 317 MenuItem item = new AddSubjectMenuItem(); 318 a.onOptionsItemSelected(item); 319 mSubjectTextEditor.setText(generateMessage()); 320 321 mTextEditor.setText(generateMessage()); 322 Button send = (Button)a.findViewById(R.id.send_button); 323 send.performClick(); 324 } 325 }; 326 327 /** 328 * Send a flurry of SMS and MMS messages 329 */ 330 @LargeTest 331 public void testSendManyMessages() throws Throwable { 332 // BTW, sending 50 messages brings up the "Sending too many messages" alert so 333 // backing down to a smaller number. 334 final int MAXSEND = 30; 335 final int MSG_PER_RECIPIENT = MAXSEND / mRecipients.size(); 336 final int MMS_FREQ = Math.min(MSG_PER_RECIPIENT / 10, 1); 337 338 final ComposeMessageActivity a = getActivity(); 339 for (String recipient : mRecipients) { 340 a.runOnUiThread(new Runnable() { 341 public void run() { 342 a.initialize(null); 343 a.loadMessageContent(); 344 } 345 }); 346 347 for (int i = 0; i < MSG_PER_RECIPIENT; i++) { 348 Log.v(TAG, "Sending msg: " + i); 349 if (i % MMS_FREQ == 0) { 350 mSendMmsMessage.setRecipient(recipient); 351 runTestOnUiThread(mSendMmsMessage); 352 } else { 353 mSendSmsMessage.setRecipient(recipient); 354 runTestOnUiThread(mSendSmsMessage); 355 } 356 Thread.sleep(5000); // wait 5 seconds between messages 357 } 358 } 359 assertTrue(true); 360 } 361 } 362