1
+ ///<reference path="../.d.ts"/>
2
+
3
+ import path = require( "path" ) ;
4
+ import options = require( "./../options" ) ;
5
+ import shell = require( "shelljs" ) ;
6
+ import osenv = require( "osenv" ) ;
7
+
8
+ export class ProjectService implements IProjectService {
9
+ private static DEFAULT_ID = "com.telerik.tns.HelloWorld" ;
10
+ private static DEFAULT_NAME = "HelloNativescript" ;
11
+ private static APP_FOLDER_NAME = "app" ;
12
+
13
+ constructor ( private $logger : ILogger ,
14
+ private $errors : IErrors ,
15
+ private $fs : IFileSystem ,
16
+ private $projectTemplatesService : IProjectTemplatesService ) { }
17
+
18
+ public createProject ( projectName : string , projectId : string ) : IFuture < void > {
19
+ return ( ( ) => {
20
+ var projectDir = path . resolve ( options . path || "." ) ;
21
+
22
+ projectId = projectId || ProjectService . DEFAULT_ID ;
23
+ projectName = projectName || ProjectService . DEFAULT_NAME ;
24
+
25
+ projectDir = path . join ( projectDir , projectName ) ;
26
+ this . $fs . createDirectory ( projectDir ) . wait ( ) ;
27
+
28
+ var customAppPath = this . getCustomAppPath ( ) ;
29
+ if ( customAppPath ) {
30
+ customAppPath = path . resolve ( customAppPath ) ;
31
+ }
32
+
33
+ if ( this . $fs . exists ( projectDir ) . wait ( ) && ! this . $fs . isEmptyDir ( projectDir ) . wait ( ) ) {
34
+ this . $errors . fail ( "Path already exists and is not empty %s" , projectDir ) ;
35
+ }
36
+
37
+ this . $logger . trace ( "Creating a new NativeScript project with name %s and id at location" , projectName , projectId , projectDir ) ;
38
+
39
+ var appDirectory = path . join ( projectDir , ProjectService . APP_FOLDER_NAME ) ;
40
+ var appPath : string = null ;
41
+
42
+ if ( customAppPath ) {
43
+ this . $logger . trace ( "Using custom app from %s" , customAppPath ) ;
44
+
45
+ // Make sure that the source app/ is not a direct ancestor of a target app/
46
+ var relativePathFromSourceToTarget = path . relative ( customAppPath , appDirectory ) ;
47
+ var doesRelativePathGoUpAtLeastOneDir = relativePathFromSourceToTarget . split ( path . sep ) [ 0 ] == ".." ;
48
+ if ( ! doesRelativePathGoUpAtLeastOneDir ) {
49
+ this . $errors . fail ( "Project dir %s must not be created at/inside the template used to create the project %s." , projectDir , customAppPath ) ;
50
+ }
51
+ this . $logger . trace ( "Copying custom app into %s" , appDirectory ) ;
52
+ appPath = customAppPath ;
53
+ } else {
54
+ // No custom app - use nativescript hello world application
55
+ this . $logger . trace ( "Using NativeScript hello world application" ) ;
56
+ var defaultTemplatePath = this . $projectTemplatesService . defaultTemplatePath . wait ( ) ;
57
+ this . $logger . trace ( "Copying Nativescript hello world application into %s" , appDirectory ) ;
58
+ appPath = defaultTemplatePath ;
59
+ }
60
+
61
+ this . createProjectCore ( projectDir , appPath , false ) . wait ( ) ;
62
+ } ) . future < void > ( ) ( ) ;
63
+ }
64
+
65
+ private createProjectCore ( projectDir : string , appPath : string , symlink ?: boolean ) : IFuture < void > {
66
+ return ( ( ) => {
67
+ if ( ! this . $fs . exists ( projectDir ) . wait ( ) ) {
68
+ this . $fs . createDirectory ( projectDir ) . wait ( ) ;
69
+ }
70
+ if ( symlink ) {
71
+ // TODO: Implement support for symlink the app folder instead of copying
72
+ } else {
73
+ var appDir = path . join ( projectDir , ProjectService . APP_FOLDER_NAME ) ;
74
+ this . $fs . createDirectory ( appDir ) . wait ( ) ;
75
+ shell . cp ( '-R' , path . join ( appPath , "*" ) , appDir ) ;
76
+ }
77
+ this . createBasicProjectStructure ( projectDir ) . wait ( ) ;
78
+ } ) . future < void > ( ) ( ) ;
79
+ }
80
+
81
+ private createBasicProjectStructure ( projectDir : string ) : IFuture < void > {
82
+ return ( ( ) => {
83
+ this . $fs . createDirectory ( path . join ( projectDir , "platforms" ) ) . wait ( ) ;
84
+ this . $fs . createDirectory ( path . join ( projectDir , "tns_modules" ) ) . wait ( ) ;
85
+ this . $fs . createDirectory ( path . join ( projectDir , "hooks" ) ) . wait ( ) ;
86
+ } ) . future < void > ( ) ( ) ;
87
+ }
88
+
89
+ private getCustomAppPath ( ) : string {
90
+ var customAppPath = options [ "copy-from" ] || options [ "link-to" ] ;
91
+ if ( customAppPath ) {
92
+ if ( customAppPath . indexOf ( "http" ) >= 0 ) {
93
+ this . $errors . fail ( "Only local paths for custom app are supported." ) ;
94
+ }
95
+
96
+ if ( customAppPath . substr ( 0 , 1 ) === '~' ) {
97
+ customAppPath = path . join ( osenv . home ( ) , customAppPath . substr ( 1 ) ) ;
98
+ }
99
+ }
100
+
101
+ return customAppPath ;
102
+ }
103
+ }
104
+ $injector . register ( "projectService" , ProjectService ) ;
0 commit comments