Skip to content

Commit

Permalink
Merge pull request ResearchKit#24 from EricSiegNW/feature/Bridge-663
Browse files Browse the repository at this point in the history
Feature/bridge 663 & 806
  • Loading branch information
Erin-Mounts committed Sep 30, 2015
2 parents 11f8a05 + 63fc5d1 commit 9947556
Show file tree
Hide file tree
Showing 16 changed files with 263 additions and 12 deletions.
4 changes: 3 additions & 1 deletion APCAppCore/APCAppCore.xcodeproj/project.pbxproj
Expand Up @@ -736,6 +736,7 @@
/* End PBXBuildFile section */

/* Begin PBXFileReference section */
045D0CBD1BBAFDC500330C7E /* APCModel 8.xcdatamodel */ = {isa = PBXFileReference; lastKnownFileType = wrapper.xcdatamodel; path = "APCModel 8.xcdatamodel"; sourceTree = "<group>"; };
0494397F1B8FC04000CAE23C /* APCDownloadDataViewController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = APCDownloadDataViewController.h; sourceTree = "<group>"; };
049439801B8FC04000CAE23C /* APCDownloadDataViewController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = APCDownloadDataViewController.m; sourceTree = "<group>"; };
04FB64451BB4883900D0A50D /* APCTaskImporter.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = APCTaskImporter.h; sourceTree = "<group>"; };
Expand Down Expand Up @@ -4164,6 +4165,7 @@
F5F128981A2F78490015982C /* APCModel.xcdatamodeld */ = {
isa = XCVersionGroup;
children = (
045D0CBD1BBAFDC500330C7E /* APCModel 8.xcdatamodel */,
04FB64491BB4A11A00D0A50D /* APCModel 7.xcdatamodel */,
366345791B1F84F0003CC0EF /* APCModel 6.xcdatamodel */,
366345781B1F84DD003CC0EF /* APCModel 5.xcdatamodel */,
Expand All @@ -4172,7 +4174,7 @@
36469C321AA1650F00C10CA7 /* APCModel 3.xcdatamodel */,
F5F128991A2F78490015982C /* APCModel.xcdatamodel */,
);
currentVersion = 04FB64491BB4A11A00D0A50D /* APCModel 7.xcdatamodel */;
currentVersion = 045D0CBD1BBAFDC500330C7E /* APCModel 8.xcdatamodel */;
path = APCModel.xcdatamodeld;
sourceTree = "<group>";
versionGroupType = wrapper.xcdatamodel;
Expand Down
Expand Up @@ -3,6 +3,6 @@
<plist version="1.0">
<dict>
<key>_XCCurrentVersionName</key>
<string>APCModel 7.xcdatamodel</string>
<string>APCModel 8.xcdatamodel</string>
</dict>
</plist>
@@ -0,0 +1,115 @@
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<model userDefinedModelVersionIdentifier="" type="com.apple.IDECoreDataModeler.DataModel" documentVersion="1.0" lastSavedToolsVersion="7701" systemVersion="14D136" minimumToolsVersion="Xcode 4.3" macOSVersion="Automatic" iOSVersion="Automatic">
<entity name="APCDBStatus" representedClassName="APCDBStatus" syncable="YES">
<attribute name="status" optional="YES" attributeType="String" syncable="YES"/>
</entity>
<entity name="APCMedTrackerDailyDosageRecord" representedClassName="APCMedTrackerDailyDosageRecord" syncable="YES">
<attribute name="dateThisRecordRepresents" attributeType="Date" indexed="YES" syncable="YES"/>
<attribute name="numberOfDosesTakenForThisDate" attributeType="Integer 16" minValueString="0" defaultValueString="0" syncable="YES"/>
<relationship name="prescriptionIAmBasedOn" maxCount="1" deletionRule="Nullify" destinationEntity="APCMedTrackerPrescription" inverseName="actualDosesTaken" inverseEntity="APCMedTrackerPrescription" syncable="YES"/>
</entity>
<entity name="APCMedTrackerInflatableItem" representedClassName="APCMedTrackerInflatableItem" syncable="YES">
<attribute name="name" attributeType="String" minValueString="1" indexed="YES" syncable="YES"/>
</entity>
<entity name="APCMedTrackerMedication" representedClassName="APCMedTrackerMedication" parentEntity="APCMedTrackerInflatableItem" syncable="YES">
<relationship name="prescriptionsWhereIAmUsed" optional="YES" toMany="YES" deletionRule="Nullify" destinationEntity="APCMedTrackerPrescription" inverseName="medication" inverseEntity="APCMedTrackerPrescription" syncable="YES"/>
</entity>
<entity name="APCMedTrackerPossibleDosage" representedClassName="APCMedTrackerPossibleDosage" parentEntity="APCMedTrackerInflatableItem" syncable="YES">
<attribute name="amount" optional="YES" attributeType="Float" minValueString="0" syncable="YES"/>
<relationship name="prescriptionsWhereIAmUsed" optional="YES" toMany="YES" minCount="1" deletionRule="Nullify" destinationEntity="APCMedTrackerPrescription" inverseName="dosage" inverseEntity="APCMedTrackerPrescription" syncable="YES"/>
</entity>
<entity name="APCMedTrackerPrescription" representedClassName="APCMedTrackerPrescription" syncable="YES">
<attribute name="dateStartedUsing" attributeType="Date" syncable="YES"/>
<attribute name="dateStoppedUsing" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="didStopUsingOnDoctorsOrders" optional="YES" attributeType="Boolean" syncable="YES"/>
<attribute name="numberOfTimesPerDay" attributeType="Integer 16" minValueString="0" defaultValueString="0" syncable="YES"/>
<attribute name="zeroBasedDaysOfTheWeek" attributeType="String" syncable="YES"/>
<relationship name="actualDosesTaken" optional="YES" toMany="YES" deletionRule="Nullify" destinationEntity="APCMedTrackerDailyDosageRecord" inverseName="prescriptionIAmBasedOn" inverseEntity="APCMedTrackerDailyDosageRecord" syncable="YES"/>
<relationship name="color" optional="YES" maxCount="1" deletionRule="Nullify" destinationEntity="APCMedTrackerPrescriptionColor" inverseName="prescriptionsWhereIAmUsed" inverseEntity="APCMedTrackerPrescriptionColor" syncable="YES"/>
<relationship name="dosage" optional="YES" maxCount="1" deletionRule="Nullify" destinationEntity="APCMedTrackerPossibleDosage" inverseName="prescriptionsWhereIAmUsed" inverseEntity="APCMedTrackerPossibleDosage" syncable="YES"/>
<relationship name="medication" maxCount="1" deletionRule="Nullify" destinationEntity="APCMedTrackerMedication" inverseName="prescriptionsWhereIAmUsed" inverseEntity="APCMedTrackerMedication" syncable="YES"/>
</entity>
<entity name="APCMedTrackerPrescriptionColor" representedClassName="APCMedTrackerPrescriptionColor" parentEntity="APCMedTrackerInflatableItem" syncable="YES">
<attribute name="alphaAsFloat" attributeType="Float" minValueString="0" maxValueString="1" defaultValueString="1" syncable="YES"/>
<attribute name="blueAsInteger" attributeType="Integer 16" minValueString="0" maxValueString="255" defaultValueString="50" syncable="YES"/>
<attribute name="greenAsInteger" optional="YES" attributeType="Integer 16" minValueString="0" maxValueString="255" defaultValueString="50" syncable="YES"/>
<attribute name="naturalSortOrder" optional="YES" attributeType="Integer 16" minValueString="0" defaultValueString="0" indexed="YES" syncable="YES"/>
<attribute name="redAsInteger" optional="YES" attributeType="Integer 16" minValueString="0" maxValueString="255" defaultValueString="50" syncable="YES"/>
<relationship name="prescriptionsWhereIAmUsed" optional="YES" toMany="YES" deletionRule="Nullify" destinationEntity="APCMedTrackerPrescription" inverseName="color" inverseEntity="APCMedTrackerPrescription" syncable="YES"/>
</entity>
<entity name="APCResult" representedClassName="APCResult" syncable="YES">
<attribute name="archiveFilename" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="createdAt" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="endDate" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="metaData" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="resultSummary" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="startDate" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="taskID" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="taskRunID" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="updatedAt" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="uploaded" optional="YES" attributeType="Boolean" syncable="YES"/>
<relationship name="task" optional="YES" maxCount="1" deletionRule="Nullify" destinationEntity="APCTask" inverseName="results" inverseEntity="APCTask" syncable="YES"/>
</entity>
<entity name="APCStoredUserData" representedClassName="APCStoredUserData" syncable="YES">
<attribute name="allowContact" optional="YES" attributeType="Boolean" syncable="YES"/>
<attribute name="biologicalSex" optional="YES" attributeType="Integer 16" defaultValueString="0" syncable="YES"/>
<attribute name="birthDate" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="bloodType" optional="YES" attributeType="Integer 16" defaultValueString="0" syncable="YES"/>
<attribute name="consentSignatureDate" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="consentSignatureImage" optional="YES" attributeType="Binary" allowsExternalBinaryDataStorage="YES" syncable="YES"/>
<attribute name="consentSignatureName" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="customSurveyQuestion" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="dailyScalesCompletionCounter" optional="YES" attributeType="Integer 64" defaultValueString="0" syncable="YES"/>
<attribute name="ethnicity" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="glucoseLevels" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="hasHeartDisease" optional="YES" attributeType="Integer 64" defaultValueString="0" syncable="YES"/>
<attribute name="homeLocationAddress" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="homeLocationLat" optional="YES" attributeType="Float" defaultValueString="0.0" syncable="YES"/>
<attribute name="homeLocationLong" optional="YES" attributeType="Float" defaultValueString="0.0" syncable="YES"/>
<attribute name="medicalConditions" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="medications" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="phoneNumber" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="profileImage" optional="YES" attributeType="Binary" allowsExternalBinaryDataStorage="YES" syncable="YES"/>
<attribute name="secondaryInfoSaved" optional="YES" attributeType="Boolean" syncable="YES"/>
<attribute name="serverConsented" optional="YES" attributeType="Boolean" syncable="YES"/>
<attribute name="sharedOptionSelection" optional="YES" attributeType="Integer 64" defaultValueString="0" syncable="YES"/>
<attribute name="sleepTime" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="taskCompletion" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="userConsented" optional="YES" attributeType="Boolean" syncable="YES"/>
<attribute name="wakeUpTime" optional="YES" attributeType="Date" syncable="YES"/>
</entity>
<entity name="APCTask" representedClassName="APCTask" syncable="YES">
<attribute name="createdAt" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="sortString" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="taskClassName" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="taskCompletionTimeString" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="taskContentFileName" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="taskDescription" optional="YES" attributeType="Binary" syncable="YES"/>
<attribute name="taskExpires" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="taskFinished" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="taskGuid" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="taskHRef" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="taskID" optional="YES" attributeType="String" indexed="YES" syncable="YES"/>
<attribute name="taskIsOptional" optional="YES" attributeType="Boolean" syncable="YES"/>
<attribute name="taskScheduledFor" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="taskStarted" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="taskTitle" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="taskType" optional="YES" attributeType="Integer 32" defaultValueString="0" syncable="YES"/>
<attribute name="taskVersionDate" optional="YES" attributeType="Date" syncable="YES"/>
<attribute name="taskVersionName" optional="YES" attributeType="String" syncable="YES"/>
<attribute name="updatedAt" optional="YES" attributeType="Date" syncable="YES"/>
<relationship name="results" optional="YES" toMany="YES" deletionRule="Nullify" destinationEntity="APCResult" inverseName="task" inverseEntity="APCResult" syncable="YES"/>
</entity>
<elements>
<element name="APCDBStatus" positionX="-1341" positionY="72" width="171" height="58"/>
<element name="APCMedTrackerDailyDosageRecord" positionX="-1188" positionY="621" width="216" height="88"/>
<element name="APCMedTrackerInflatableItem" positionX="-965" positionY="1080" width="299" height="58"/>
<element name="APCMedTrackerMedication" positionX="-1260" positionY="935" width="180" height="58"/>
<element name="APCMedTrackerPossibleDosage" positionX="-1269" positionY="758" width="216" height="73"/>
<element name="APCMedTrackerPrescription" positionX="-938" positionY="764" width="218" height="178"/>
<element name="APCMedTrackerPrescriptionColor" positionX="-666" positionY="729" width="207" height="133"/>
<element name="APCResult" positionX="-1359" positionY="297" width="171" height="210"/>
<element name="APCStoredUserData" positionX="-1593" positionY="72" width="200" height="435"/>
<element name="APCTask" positionX="-873" positionY="71" width="207" height="345"/>
</elements>
</model>
2 changes: 2 additions & 0 deletions APCAppCore/APCAppCore/DataSubstrate/Model/APCTask+Bridge.m
Expand Up @@ -113,6 +113,8 @@ - (void) loadSurveyOnCompletion: (void (^)(NSError * error)) completionBlock
SBBSurvey * sbbSurvey = (SBBSurvey*) survey;
[self.managedObjectContext performBlockAndWait:^{
self.taskTitle = sbbSurvey.name;
self.taskVersionName = sbbSurvey.guid;
self.taskVersionDate = sbbSurvey.createdOn;
self.rkTask = [APCTask rkTaskFromSBBSurvey:survey];
NSError * saveError;
[self saveToPersistentStore:&saveError];
Expand Down
4 changes: 3 additions & 1 deletion APCAppCore/APCAppCore/DataSubstrate/Model/APCTask.h
Expand Up @@ -53,7 +53,9 @@
@property (nonatomic, retain) NSDate * taskScheduledFor;
@property (nonatomic, retain) NSDate * taskStarted;
@property (nonatomic, retain) NSString * taskTitle;
@property (nonatomic, retain) NSNumber * taskVersionNumber;
@property (nonatomic, retain) NSNumber * taskType;
@property (nonatomic, retain) NSDate * taskVersionDate;
@property (nonatomic, retain) NSString * taskVersionName;
@property (nonatomic, retain) NSDate * updatedAt;
@property (nonatomic, retain) NSSet *results;
@end
Expand Down
4 changes: 3 additions & 1 deletion APCAppCore/APCAppCore/DataSubstrate/Model/APCTask.m
Expand Up @@ -52,7 +52,9 @@ @implementation APCTask
@dynamic taskScheduledFor;
@dynamic taskStarted;
@dynamic taskTitle;
@dynamic taskVersionNumber;
@dynamic taskType;
@dynamic taskVersionDate;
@dynamic taskVersionName;
@dynamic updatedAt;
@dynamic results;

Expand Down
9 changes: 4 additions & 5 deletions APCAppCore/APCAppCore/Library/APCTaskImporter.m
Expand Up @@ -91,7 +91,6 @@
static NSString * const kTaskTypeKey = @"taskType";
static NSString * const kTaskTypeValueSurvey = @"survey";
static NSString * const kTaskUrlKey = @"taskUrl";
static NSString * const kTaskVersionNumberKey = @"version";

/**
Formats for interpreting a JSON list of time values.
Expand Down Expand Up @@ -206,7 +205,6 @@ - (APCTask *) createOrUpdateTaskFromJsonData: (NSDictionary *) taskData
{
APCTask *task = nil;
NSString *taskGuid = [self nilIfNull: taskData [kTaskGuidKey]];
NSNumber *taskVersionNumber = [self nilIfNull: taskData [kTaskVersionNumberKey]];

NSSet *tasks = [APCTask querySavedTasksWithTaskGuids: [NSSet setWithObject: taskGuid]
usingContext: context];
Expand All @@ -220,7 +218,6 @@ - (APCTask *) createOrUpdateTaskFromJsonData: (NSDictionary *) taskData
{
task = [APCTask newObjectForContext: context];
task.taskGuid = taskGuid;
task.taskVersionNumber = taskVersionNumber;
}

[self updateTask: task
Expand All @@ -237,6 +234,7 @@ - (void) updateTask: (APCTask *) task
// (or add it for the first time, if we're creating a task).
//
task.taskID = [self nilIfNull: taskData [kTaskIDKey]];
task.taskType = [self nilIfNull: taskData [kTaskTypeKey]]; // internal representation of separate bridge types (Survey, non Survey)
task.taskHRef = [self nilIfNull: taskData [kTaskUrlKey]]; // bridge-only?
task.taskTitle = [self nilIfNull: taskData [kTaskTitleKey]]; // bridge and us
task.sortString = [self nilIfNull: taskData [kTaskSortStringKey]]; // appcore-only, for now
Expand Down Expand Up @@ -396,13 +394,15 @@ - (NSDictionary *) extractJsonDataFromIncomingSageTask: (SBBTask *)sageTask
taskData [kTaskSortStringKey] = [self nullIfNil: sageTask.activity.activityType]; // Default for now

if (sageTask.activity.survey) {
taskData [kTaskTypeKey] = [NSNumber numberWithUnsignedInt:APCTaskTypeSurveyTask];
taskData [kTaskIDKey] = [self nullIfNil: sageTask.activity.survey.identifier];
taskData [kTaskVersionNumberKey] = [self nullIfNil: sageTask.activity.survey.createdOn.toStringInISO8601Format];
taskData [kTaskUrlKey] = [self nullIfNil: sageTask.activity.survey.href];
taskData [kTaskClassNameKey] = NSStringFromClass ([APCGenericSurveyTaskViewController class]);

return taskData;
} else if (sageTask.activity.task) {
taskData [kTaskTypeKey] = [NSNumber numberWithUnsignedInt:APCTaskTypeActivityTask];

// Set up TaskId->TaskViewController dictionary
// TODO: move this init stuff out of a situation where it will be called many times
NSString *filePath = [[NSBundle mainBundle] pathForResource:kTaskIdToViewControllerMappingJSON ofType:@"json"];
Expand All @@ -421,7 +421,6 @@ - (NSDictionary *) extractJsonDataFromIncomingSageTask: (SBBTask *)sageTask
taskData [kTaskClassNameKey] = taskClassName;

// Not available for non survey tasks
taskData [kTaskVersionNumberKey] = [NSNull null];
taskData [kTaskUrlKey] = [NSNull null];

return taskData;
Expand Down
Expand Up @@ -67,6 +67,11 @@
- (NSInteger) cronDayOfWeekForDay: (NSInteger) dayInCurrentMonthYearAndCalendar;
- (NSNumber *) cronDayOfWeekAsNSNumberForDay: (NSNumber *) dayInCurrentMonthYearAndCalendar;

/**
Convert to a Joda time readable time string
*/
- (NSString *) toJodaReadableTimeString;


/**
Returns the integer last day of the month. For example,
Expand Down
10 changes: 10 additions & 0 deletions APCAppCore/APCAppCore/Library/Categories/NSDateComponents+Helper.m
Expand Up @@ -177,6 +177,16 @@ + (instancetype) components: (NSArray *) arrayOfNSCalendarUnits inGregorianLocal
fromDate: date];
}

- (NSString *) toJodaReadableTimeString
{
NSDate *dateForTime = [[NSDateComponents gregorianCalendar] dateFromComponents:self];

NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
[formatter setDateFormat:@"HH:mm:ss"];

return [formatter stringFromDate:dateForTime];
}


/**
Again -- we're modifying this DateComponents object, by design.
Expand Down

0 comments on commit 9947556

Please sign in to comment.