Merge lp:~milo/linaro-ci-dashboard/android-build-model-refactor into lp:linaro-ci-dashboard
- android-build-model-refactor
- Merge into trunk
Status: | Merged |
---|---|
Approved by: | Stevan Radaković |
Approved revision: | 31 |
Merged at revision: | 19 |
Proposed branch: | lp:~milo/linaro-ci-dashboard/android-build-model-refactor |
Merge into: | lp:linaro-ci-dashboard |
Diff against target: |
710 lines (+372/-60) 23 files modified
Makefile (+10/-7) README (+1/-1) dashboard/frontend/android_build/migrations/0001_initial.py (+92/-0) dashboard/frontend/android_build/models/__init__.py (+1/-0) dashboard/frontend/android_build/models/android_loop.py (+127/-0) dashboard/frontend/android_build/urls.py (+34/-0) dashboard/frontend/integration_loop/forms/integration_loop_form.py (+1/-1) dashboard/frontend/integration_loop/migrations/0001_initial.py (+50/-0) dashboard/frontend/integration_loop/models/__init__.py (+1/-0) dashboard/frontend/integration_loop/models/integration_loop.py (+1/-2) dashboard/frontend/integration_loop/urls.py (+34/-0) dashboard/frontend/integration_loop/views/integration_loop_create_view.py (+3/-3) dashboard/frontend/integration_loop/views/integration_loop_detail_view.py (+1/-1) dashboard/frontend/integration_loop/views/integration_loop_update_view.py (+3/-3) dashboard/frontend/migrations/0001_initial.py (+0/-19) dashboard/frontend/models/__init__.py (+0/-1) dashboard/frontend/models/loop.py (+0/-1) dashboard/frontend/tests/test_views.py (+6/-6) dashboard/frontend/urls.py (+1/-12) dashboard/frontend/views/index_view.py (+1/-1) dashboard/frontend/views/loop_build_view.py (+0/-2) dashboard/settings.py (+3/-0) dashboard/urls.py (+2/-0) |
To merge this branch: | bzr merge lp:~milo/linaro-ci-dashboard/android-build-model-refactor |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Stevan Radaković | code, modeling | Approve | |
Georgy Redkozubov | Approve | ||
Linaro Infrastructure | Pending | ||
Review via email: mp+119580@code.launchpad.net |
Commit message
Description of the change
This is the refactoring of the android build model, as an "inside app", under the "frontend" one.
If this is the agreed approach, I will continue and refactor the rest (mostly the integration_loop one, keeping the loop model under the frontend).
Stevan Radaković (stevanr) wrote : | # |
Thanks for refactoring things Milo.
One thing still bothers me a lot and that's the jenkins config.
In my opinion, this should not be separated from the jenkins server model, because at some point (even though the jenkins server is internally considered singleton for now), we might have more then one jenkins server connected with our app and then we will not know which config refers to which server. And it just makes sense that the jenkins server configuration is part of the jenkins server itself, n'est-ce pas? :)
So if you agree with this there are two possible solutions that I see (with me routing for the first one):
1. Remove the config model and add the two fields (config_template and config) to the jenkins server model.
2. Keep the config model, but add one-to-one relation between config model and jenkins server model. This will make the relation between the Loop and the JenkinsConfig models obsolete so it should be removed.
Georgy Redkozubov (gesha) wrote : | # |
> Thanks for refactoring things Milo.
>
> One thing still bothers me a lot and that's the jenkins config.
> In my opinion, this should not be separated from the jenkins server model,
> because at some point (even though the jenkins server is internally considered
> singleton for now), we might have more then one jenkins server connected with
> our app and then we will not know which config refers to which server. And it
> just makes sense that the jenkins server configuration is part of the jenkins
> server itself, n'est-ce pas? :)
Good point, but the it's not bound to the jenkins server, ok, better to say it's a job config for a particular loop which configuration is based on the template and filled with the data before sending it to jenkins job.
There were 3 options:
1) Generate all needed job config fields on the fly from DB when creating/updating job.
2) Add fields to Loop model and do it once when creating/updating job.
3) Add new model and link it to Loop and do it once when creating/updating job.
Second approach wonn't work for us, in case we need to add new configuration fields we have to update all loops.
First and third approaches are similar.
We decided to go third way. We can have common configuration fields like 'command', 'config' generated in one place and specific to particular loop type generate in that loop class.
May be I'm making things complicate and there is easier way? :)
>
> So if you agree with this there are two possible solutions that I see (with me
> routing for the first one):
> 1. Remove the config model and add the two fields (config_template and config)
> to the jenkins server model.
> 2. Keep the config model, but add one-to-one relation between config model and
> jenkins server model. This will make the relation between the Loop and the
> JenkinsConfig models obsolete so it should be removed.
Stevan Radaković (stevanr) wrote : | # |
> > Thanks for refactoring things Milo.
> >
> > One thing still bothers me a lot and that's the jenkins config.
> > In my opinion, this should not be separated from the jenkins server model,
> > because at some point (even though the jenkins server is internally
> considered
> > singleton for now), we might have more then one jenkins server connected
> with
> > our app and then we will not know which config refers to which server. And
> it
> > just makes sense that the jenkins server configuration is part of the
> jenkins
> > server itself, n'est-ce pas? :)
>
> Good point, but the it's not bound to the jenkins server, ok, better to say
> it's a job config for a particular loop which configuration is based on the
> template and filled with the data before sending it to jenkins job.
> There were 3 options:
> 1) Generate all needed job config fields on the fly from DB when
> creating/updating job.
> 2) Add fields to Loop model and do it once when creating/updating job.
> 3) Add new model and link it to Loop and do it once when creating/updating
> job.
> Second approach wonn't work for us, in case we need to add new configuration
> fields we have to update all loops.
> First and third approaches are similar.
> We decided to go third way. We can have common configuration fields like
> 'command', 'config' generated in one place and specific to particular loop
> type generate in that loop class.
> May be I'm making things complicate and there is easier way? :)
>
Ok sorry I didn't know that it's representing a job config since it's called the JenkinsConfig and it's part of the jenkinsserver APP, so I realized it's representing general Jenkins server configuration.
With that thing cleared up, I would like us to remember general guidelines for the CI Loops development presented by Danilo couple of weeks ago. The point was that we have as small amount of dependency on jenkins in our frontend app as possible.
In my opinion this new dependency is redundant since we must update the jenkins job each time the loop is created or updated anyway, so why keep it in the DB when we must do it on-the-fly anyway.
If we rly want to keep the job config anyway, I'd suggest linking it with loop the other way around, by putting loop_id as foreign key in JenkinsConfig (which should be renamed anyway if we decide to keep it) and adding unique constraint, so it's one-on-one relationship. Of course, all the updates to the jenkins config table should then be from the jenkinsserver up, and in no case from the frontend.
I hope this clears up the things a bit..
> >
> > So if you agree with this there are two possible solutions that I see (with
> me
> > routing for the first one):
> > 1. Remove the config model and add the two fields (config_template and
> config)
> > to the jenkins server model.
> > 2. Keep the config model, but add one-to-one relation between config model
> and
> > jenkins server model. This will make the relation between the Loop and the
> > JenkinsConfig models obsolete so it should be removed.
Milo Casagrande (milo) wrote : | # |
On Wed, Aug 15, 2012 at 12:50 PM, Stevan Radaković
<email address hidden> wrote:
>
> Ok sorry I didn't know that it's representing a job config since it's called the JenkinsConfig and it's part of the jenkinsserver APP, so I realized it's representing general Jenkins server configuration.
Our bad on choosing that name I guess... but as gesha explained, is a
parameter necessary for the the Android Build job, and is called
CONFIG inside Jenkins.
> With that thing cleared up, I would like us to remember general guidelines for the CI Loops development presented by Danilo couple of weeks ago. The point was that we have as small amount of dependency on jenkins in our frontend app as possible.
Yep, that is right.
> In my opinion this new dependency is redundant since we must update the jenkins job each time the loop is created or updated anyway, so why keep it in the DB when we must do it on-the-fly anyway.
From what I saw from the Android builds, they are updated seldomly.
Once a loop is created and doesn't explode, it is left like that.
The on-the-fly option was considered, but since jobs are not updated
that much, it made more sense to store that parameter somewhere and
retrieve it. I think it is more of a tradeoff between taking up a
little bit more space, than starting to create base64 encoded strings
for all the builds on the fly.
> If we rly want to keep the job config anyway, I'd suggest linking it with loop the other way around, by putting loop_id as foreign key in JenkinsConfig (which should be renamed anyway if we decide to keep it) and adding unique constraint, so it's one-on-one relationship. Of course, all the updates to the jenkins config table should then be from the jenkinsserver up, and in no case from the frontend.
Name will be changed, for sure.
Good point about reverting the direction of the relationship. For the
constraint I was considering it, but didn't add it since I wanted to
see if we needed other fields in there that could have been unique
together too.
Another thing, since this is only related to Android, could be to
extend the android_loop model and store the base64 encoded "CONFIG" in
there.
--
Milo Casagrande
Infrastructure Engineer
Linaro.org <www.linaro.org> │ Open source software for ARM SoCs
- 27. By Milo Casagrande
-
Removed JenkinsConfig.
Milo Casagrande (milo) wrote : | # |
With revno 27 I removed the JenkinsConfig class as discussed during the meeting.
- 28. By Milo Casagrande
-
Removed jenkins_config from migrations.
- 29. By Milo Casagrande
-
integration_loop as subapps inside frontend.
- 30. By Milo Casagrande
-
Fixed Makefile, fixed imports in tests.
- 31. By Milo Casagrande
-
Fixed problems with tests (remember to clear up .pyc files).
Milo Casagrande (milo) wrote : | # |
With revno 31 there is the final refactoring of integration_loop as a subapp, and tests are now fixed (had problems with .pyc files around in the projects dir).
Stevan Radaković (stevanr) wrote : | # |
I thinks we will still need to talk about the layout of subapps in the frontend app, but this is good enough for landing, we can easily refactor later.
Approve +1.
Preview Diff
1 | === modified file 'Makefile' |
2 | --- Makefile 2012-07-19 08:00:53 +0000 |
3 | +++ Makefile 2012-08-17 07:43:18 +0000 |
4 | @@ -1,17 +1,21 @@ |
5 | # Makefile for linaro-ci-dashboard |
6 | |
7 | help: |
8 | - @echo "Please use \`make <target>' where <target> is one of" |
9 | - @echo " migration to update the database schema with the" \ |
10 | + @echo "Please use \`make <target>' where <target> is one of:" |
11 | + @echo " create-migration to update the database schema with the" \ |
12 | "latest model changes" |
13 | - @echo " runserver to run the django web server" |
14 | - @echo " test to run the unit tests" |
15 | + @echo " runserver to run the django web server" |
16 | + @echo " test to run the unit tests" |
17 | |
18 | create-migration: syncdb |
19 | python dashboard/manage.py schemamigration frontend --auto || \ |
20 | echo "No changes to frontend models." |
21 | - python dashboard/manage.py schemamigration jenkins --auto || \ |
22 | + python dashboard/manage.py schemamigration jenkinsserver --auto || \ |
23 | echo "No changes to jenkins models." |
24 | + python dashboard/manage.py schemamigration android_build --auto || \ |
25 | + echo "No changes to android_build models." |
26 | + python dashboard/manage.py schemamigration integration_loop --auto || \ |
27 | + echo "No changes to integration_loop models." |
28 | python dashboard/manage.py migrate |
29 | |
30 | migrate: syncdb |
31 | @@ -25,7 +29,6 @@ |
32 | |
33 | test: |
34 | python dashboard/manage.py jenkins start |
35 | - python dashboard/manage.py test frontend \ |
36 | - jenkinsserver |
37 | + python dashboard/manage.py test frontend jenkinsserver |
38 | |
39 | .PHONY: help migration test |
40 | |
41 | === modified file 'README' |
42 | --- README 2012-07-24 21:34:26 +0000 |
43 | +++ README 2012-08-17 07:43:18 +0000 |
44 | @@ -46,7 +46,7 @@ |
45 | Whenever any of the models are changed, it is strongly advised to run |
46 | South' schemamigration command: |
47 | |
48 | - $ make migration |
49 | + $ make migrate |
50 | |
51 | |
52 | Tests |
53 | |
54 | === added directory 'dashboard/frontend/android_build' |
55 | === added file 'dashboard/frontend/android_build/__init__.py' |
56 | === added directory 'dashboard/frontend/android_build/migrations' |
57 | === added file 'dashboard/frontend/android_build/migrations/0001_initial.py' |
58 | --- dashboard/frontend/android_build/migrations/0001_initial.py 1970-01-01 00:00:00 +0000 |
59 | +++ dashboard/frontend/android_build/migrations/0001_initial.py 2012-08-17 07:43:18 +0000 |
60 | @@ -0,0 +1,92 @@ |
61 | +# encoding: utf-8 |
62 | +import datetime |
63 | +from south.db import db |
64 | +from south.v2 import SchemaMigration |
65 | +from django.db import models |
66 | + |
67 | +class Migration(SchemaMigration): |
68 | + |
69 | + def forwards(self, orm): |
70 | + |
71 | + # Adding model 'AndroidLoop' |
72 | + db.create_table('android_build_androidloop', ( |
73 | + ('loop_ptr', self.gf('django.db.models.fields.related.OneToOneField')(to=orm['frontend.Loop'], unique=True, primary_key=True)), |
74 | + ('build_type', self.gf('django.db.models.fields.CharField')(max_length=100)), |
75 | + ('manifest_repo', self.gf('django.db.models.fields.CharField')(default='git://android.git.kernel.org/platform/manifest.git', max_length=255)), |
76 | + ('manifest_branch', self.gf('django.db.models.fields.CharField')(default='master', max_length=50)), |
77 | + ('repo_quiet', self.gf('django.db.models.fields.BooleanField')(default=False)), |
78 | + ('manifest_filename', self.gf('django.db.models.fields.CharField')(default='default.xml', max_length=255)), |
79 | + ('make_targets', self.gf('django.db.models.fields.CharField')(max_length=255, blank=True)), |
80 | + ('make_jobs', self.gf('django.db.models.fields.PositiveIntegerField')(default=0)), |
81 | + ('ramdisk_size', self.gf('django.db.models.fields.PositiveIntegerField')(default=0)), |
82 | + ('external_tarball', self.gf('django.db.models.fields.CharField')(max_length=255, blank=True)), |
83 | + ('build_fs_image', self.gf('django.db.models.fields.BooleanField')(default=False)), |
84 | + ('fs_image_size', self.gf('django.db.models.fields.CharField')(default='2G', max_length=20, blank=True)), |
85 | + ('user_defined_values', self.gf('django.db.models.fields.TextField')(blank=True)), |
86 | + ('toolchain_url', self.gf('django.db.models.fields.CharField')(max_length=255, blank=True)), |
87 | + ('target_product', self.gf('django.db.models.fields.CharField')(max_length=50, blank=True)), |
88 | + ('target_tools_prefix', self.gf('django.db.models.fields.CharField')(max_length=255, blank=True)), |
89 | + ('binutils_version', self.gf('django.db.models.fields.CharField')(default='2.20.1', max_length=25)), |
90 | + ('binutils_url', self.gf('django.db.models.fields.CharField')(max_length=255, blank=True)), |
91 | + ('gcc_version', self.gf('django.db.models.fields.CharField')(default='4.4.0', max_length=25)), |
92 | + ('gcc_url', self.gf('django.db.models.fields.CharField')(max_length=255, blank=True)), |
93 | + ('sysroot_ndk_url', self.gf('django.db.models.fields.CharField')(max_length=255, blank=True)), |
94 | + ('lava_submit', self.gf('django.db.models.fields.BooleanField')(default=False)), |
95 | + ('lava_test_plan', self.gf('django.db.models.fields.CharField')(max_length=255, blank=True)), |
96 | + ('lava_submit_fatal', self.gf('django.db.models.fields.BooleanField')(default=True)), |
97 | + ('lava_android_binaries', self.gf('django.db.models.fields.BooleanField')(default=True)), |
98 | + )) |
99 | + db.send_create_signal('android_build', ['AndroidLoop']) |
100 | + |
101 | + |
102 | + def backwards(self, orm): |
103 | + |
104 | + # Deleting model 'AndroidLoop' |
105 | + db.delete_table('android_build_androidloop') |
106 | + |
107 | + |
108 | + models = { |
109 | + 'android_build.androidloop': { |
110 | + 'Meta': {'object_name': 'AndroidLoop', '_ormbases': ['frontend.Loop']}, |
111 | + 'binutils_url': ('django.db.models.fields.CharField', [], {'max_length': '255', 'blank': 'True'}), |
112 | + 'binutils_version': ('django.db.models.fields.CharField', [], {'default': "'2.20.1'", 'max_length': '25'}), |
113 | + 'build_fs_image': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), |
114 | + 'build_type': ('django.db.models.fields.CharField', [], {'max_length': '100'}), |
115 | + 'external_tarball': ('django.db.models.fields.CharField', [], {'max_length': '255', 'blank': 'True'}), |
116 | + 'fs_image_size': ('django.db.models.fields.CharField', [], {'default': "'2G'", 'max_length': '20', 'blank': 'True'}), |
117 | + 'gcc_url': ('django.db.models.fields.CharField', [], {'max_length': '255', 'blank': 'True'}), |
118 | + 'gcc_version': ('django.db.models.fields.CharField', [], {'default': "'4.4.0'", 'max_length': '25'}), |
119 | + 'lava_android_binaries': ('django.db.models.fields.BooleanField', [], {'default': 'True'}), |
120 | + 'lava_submit': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), |
121 | + 'lava_submit_fatal': ('django.db.models.fields.BooleanField', [], {'default': 'True'}), |
122 | + 'lava_test_plan': ('django.db.models.fields.CharField', [], {'max_length': '255', 'blank': 'True'}), |
123 | + 'loop_ptr': ('django.db.models.fields.related.OneToOneField', [], {'to': "orm['frontend.Loop']", 'unique': 'True', 'primary_key': 'True'}), |
124 | + 'make_jobs': ('django.db.models.fields.PositiveIntegerField', [], {'default': '0'}), |
125 | + 'make_targets': ('django.db.models.fields.CharField', [], {'max_length': '255', 'blank': 'True'}), |
126 | + 'manifest_branch': ('django.db.models.fields.CharField', [], {'default': "'master'", 'max_length': '50'}), |
127 | + 'manifest_filename': ('django.db.models.fields.CharField', [], {'default': "'default.xml'", 'max_length': '255'}), |
128 | + 'manifest_repo': ('django.db.models.fields.CharField', [], {'default': "'git://android.git.kernel.org/platform/manifest.git'", 'max_length': '255'}), |
129 | + 'ramdisk_size': ('django.db.models.fields.PositiveIntegerField', [], {'default': '0'}), |
130 | + 'repo_quiet': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), |
131 | + 'sysroot_ndk_url': ('django.db.models.fields.CharField', [], {'max_length': '255', 'blank': 'True'}), |
132 | + 'target_product': ('django.db.models.fields.CharField', [], {'max_length': '50', 'blank': 'True'}), |
133 | + 'target_tools_prefix': ('django.db.models.fields.CharField', [], {'max_length': '255', 'blank': 'True'}), |
134 | + 'toolchain_url': ('django.db.models.fields.CharField', [], {'max_length': '255', 'blank': 'True'}), |
135 | + 'user_defined_values': ('django.db.models.fields.TextField', [], {'blank': 'True'}) |
136 | + }, |
137 | + 'frontend.loop': { |
138 | + 'Meta': {'object_name': 'Loop'}, |
139 | + 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), |
140 | + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '200'}), |
141 | + 'server': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['jenkinsserver.JenkinsServer']"}) |
142 | + }, |
143 | + 'jenkinsserver.jenkinsserver': { |
144 | + 'Meta': {'object_name': 'JenkinsServer'}, |
145 | + 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), |
146 | + 'password': ('django.db.models.fields.CharField', [], {'max_length': '100'}), |
147 | + 'url': ('django.db.models.fields.CharField', [], {'max_length': '255'}), |
148 | + 'username': ('django.db.models.fields.CharField', [], {'max_length': '100'}) |
149 | + } |
150 | + } |
151 | + |
152 | + complete_apps = ['android_build'] |
153 | |
154 | === added file 'dashboard/frontend/android_build/migrations/__init__.py' |
155 | === added directory 'dashboard/frontend/android_build/models' |
156 | === added file 'dashboard/frontend/android_build/models/__init__.py' |
157 | --- dashboard/frontend/android_build/models/__init__.py 1970-01-01 00:00:00 +0000 |
158 | +++ dashboard/frontend/android_build/models/__init__.py 2012-08-17 07:43:18 +0000 |
159 | @@ -0,0 +1,1 @@ |
160 | +from frontend.android_build.models.android_loop import AndroidLoop |
161 | |
162 | === added file 'dashboard/frontend/android_build/models/android_loop.py' |
163 | --- dashboard/frontend/android_build/models/android_loop.py 1970-01-01 00:00:00 +0000 |
164 | +++ dashboard/frontend/android_build/models/android_loop.py 2012-08-17 07:43:18 +0000 |
165 | @@ -0,0 +1,127 @@ |
166 | +# Copyright (C) 2012 Linaro |
167 | +# |
168 | +# This file is part of linaro-ci-dashboard. |
169 | +# |
170 | +# linaro-ci-dashboard is free software: you can redistribute it and/or modify |
171 | +# it under the terms of the GNU Affero General Public License as published by |
172 | +# the Free Software Foundation, either version 3 of the License, or |
173 | +# (at your option) any later version. |
174 | +# |
175 | +# linaro-ci-dashboard is distributed in the hope that it will be useful, |
176 | +# but WITHOUT ANY WARRANTY; without even the implied warranty of |
177 | +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
178 | +# GNU Affero General Public License for more details. |
179 | +# |
180 | +# You should have received a copy of the GNU Affero General Public License |
181 | +# along with linaro-ci-dashboard. If not, see <http://www.gnu.org/licenses/>. |
182 | + |
183 | +from django.db import models |
184 | +from frontend.models.loop import Loop |
185 | +from jenkinsserver.models.jenkins_server import JenkinsServer |
186 | + |
187 | + |
188 | +# The internal names for the different build type, and a user visible name |
189 | +BUILD_ANDROID = (r'build-android', 'Android') |
190 | +BUILD_ANDROID_RESTRICTED = (r'build-android-restricted', 'Android Restricted') |
191 | +BUILD_ANDROID_TOOLCHAIN = (r'build-android-toolchain', 'Android Toolchain') |
192 | +BUILD_ANDROID_TOOLCHAIN_LINARO = (r'build-android-toolchain-linaro', |
193 | + 'Android Toolchain Linaro') |
194 | +# All the supported build types. |
195 | +ANDROID_BUILD_TYPES = ( |
196 | + BUILD_ANDROID, |
197 | + BUILD_ANDROID_RESTRICTED, |
198 | + BUILD_ANDROID_TOOLCHAIN, |
199 | + BUILD_ANDROID_TOOLCHAIN_LINARO, |
200 | + ) |
201 | + |
202 | +# Inetrnal name of the board, and a user visible name |
203 | +BEAGLEBOARD = (r'beagleboard', 'Beagleboard') |
204 | +PANDABOARD = (r'panda', 'Pandaboard') |
205 | +SNOWBALL = (r'snowball', 'Snowball') |
206 | +# The supported boards for the build. |
207 | +TARGET_BOARDS = (BEAGLEBOARD, PANDABOARD, SNOWBALL) |
208 | + |
209 | + |
210 | +class AndroidLoop(Loop): |
211 | + """Defines the base class for an Android integration loop.""" |
212 | + class Meta: |
213 | + app_label = 'android_build' |
214 | + |
215 | + # The default file name for the manifest file. |
216 | + DEFAULT_MANIFEST_FILE = 'default.xml' |
217 | + DEFAULT_REPO = 'git://android.git.kernel.org/platform/manifest.git' |
218 | + DEFAULT_BRANCH = 'master' |
219 | + DEFAULT_BINUTILS = '2.20.1' |
220 | + DEFAULT_GCC = '4.4.0' |
221 | + DEFAULT_IMAGE_SIZE = '2G' |
222 | + |
223 | + # BUILD_TYPE |
224 | + build_type = models.CharField(max_length=100, choices=ANDROID_BUILD_TYPES) |
225 | + # MANIFEST_REPO |
226 | + manifest_repo = models.CharField(max_length=255, default=DEFAULT_REPO) |
227 | + # MANIFEST_BRANCH |
228 | + manifest_branch = models.CharField(max_length=50, default=DEFAULT_BRANCH) |
229 | + # REPO_QUIET |
230 | + repo_quiet = models.BooleanField(default=False) |
231 | + # MANIFEST_FILENAME |
232 | + manifest_filename = models.CharField(max_length=255, |
233 | + default=DEFAULT_MANIFEST_FILE) |
234 | + # MAKE_TARGETS |
235 | + make_targets = models.CharField(max_length=255, blank=True) |
236 | + # MAKE_JOBS |
237 | + make_jobs = models.PositiveIntegerField(default=0) |
238 | + # RAMDISK_SIZE |
239 | + ramdisk_size = models.PositiveIntegerField(default=0) |
240 | + # EXTERNAL_TARBALL |
241 | + external_tarball = models.CharField(max_length=255, blank=True) |
242 | + # BUILD_FS_IMAGE |
243 | + build_fs_image = models.BooleanField(default=False, |
244 | + verbose_name='Build filesystem image') |
245 | + # FS_IMAGE_SIZE |
246 | + fs_image_size = models.CharField(max_length=20, |
247 | + blank=True, |
248 | + verbose_name='Filesystem image size', |
249 | + default=DEFAULT_IMAGE_SIZE) |
250 | + # Users might want to define their own values. |
251 | + user_defined_values = models.TextField(blank=True) |
252 | + |
253 | + # Data needed for build of type build-android. |
254 | + toolchain_url = models.CharField(max_length=255, blank=True) |
255 | + target_product = models.CharField(max_length=50, choices=TARGET_BOARDS, |
256 | + blank=True) |
257 | + target_tools_prefix = models.CharField(max_length=255, blank=True) |
258 | + |
259 | + # Data needed for build of type build-android-toolchain. |
260 | + binutils_version = models.CharField(max_length=25, |
261 | + default=DEFAULT_BINUTILS) |
262 | + binutils_url = models.CharField(max_length=255, blank=True) |
263 | + |
264 | + gcc_version = models.CharField(max_length=25, default=DEFAULT_GCC) |
265 | + gcc_url = models.CharField(max_length=255, blank=True) |
266 | + |
267 | + # TODO need to check the default value for this one. |
268 | + sysroot_ndk_url = models.CharField(max_length=255, blank=True) |
269 | + |
270 | + # Data needed for LAVA integration. |
271 | + lava_submit = models.BooleanField(default=False) |
272 | + # TODO need to know the values here |
273 | + lava_test_plan = models.CharField(max_length=255, blank=True) |
274 | + lava_submit_fatal = models.BooleanField(default=True, blank=True) |
275 | + lava_android_binaries = models.BooleanField(default=True, blank=True) |
276 | + |
277 | + def save(self, *args, **kwargs): |
278 | + self.server = JenkinsServer.objects.get(id=1) |
279 | + super(AndroidLoop, self).save(*args, **kwargs) |
280 | + # We do not want a failure in remote server to affect the |
281 | + # CI Loop flow. |
282 | + try: |
283 | + self.server.create_or_update_integration_loop(self) |
284 | + except: |
285 | + # TODO: Log error. |
286 | + pass |
287 | + |
288 | + def schedule_build(self): |
289 | + # Every time before the build is scheduled, update the |
290 | + # loop config on the remote server. |
291 | + self.server.create_or_update_integration_loop(self) |
292 | + super(AndroidLoop, self).schedule_build() |
293 | |
294 | === added directory 'dashboard/frontend/android_build/templates' |
295 | === added file 'dashboard/frontend/android_build/templates/__init__.py' |
296 | === added directory 'dashboard/frontend/android_build/tests' |
297 | === added file 'dashboard/frontend/android_build/tests/__init__.py' |
298 | === added file 'dashboard/frontend/android_build/urls.py' |
299 | --- dashboard/frontend/android_build/urls.py 1970-01-01 00:00:00 +0000 |
300 | +++ dashboard/frontend/android_build/urls.py 2012-08-17 07:43:18 +0000 |
301 | @@ -0,0 +1,34 @@ |
302 | +# Copyright (C) 2012 Linaro |
303 | +# |
304 | +# This file is part of linaro-ci-dashboard. |
305 | +# |
306 | +# linaro-ci-dashboard is free software: you can redistribute it and/or modify |
307 | +# it under the terms of the GNU Affero General Public License as published by |
308 | +# the Free Software Foundation, either version 3 of the License, or |
309 | +# (at your option) any later version. |
310 | +# |
311 | +# linaro-ci-dashboard is distributed in the hope that it will be useful, |
312 | +# but WITHOUT ANY WARRANTY; without even the implied warranty of |
313 | +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
314 | +# GNU Affero General Public License for more details. |
315 | +# |
316 | +# You should have received a copy of the GNU Affero General Public License |
317 | +# along with linaro-ci-dashboard. If not, see <http://www.gnu.org/licenses/>. |
318 | + |
319 | +from django.conf.urls.defaults import patterns, include, url |
320 | +from frontend.integration_loop.views.integration_loop_create_view \ |
321 | + import IntegrationLoopCreateView |
322 | +from frontend.integration_loop.views.integration_loop_update_view \ |
323 | + import IntegrationLoopUpdateView |
324 | +from frontend.integration_loop.views.integration_loop_detail_view \ |
325 | + import IntegrationLoopDetailView |
326 | + |
327 | + |
328 | +urlpatterns = patterns('', |
329 | + url(r'^android/create/$', |
330 | + IntegrationLoopCreateView.as_view(), name='AndroidLoopCreate'), |
331 | + url(r'^android/detail/(?P<slug>[\w|\W]+)/$', |
332 | + IntegrationLoopDetailView.as_view(), name='AndroidLoopDetail'), |
333 | + url(r'^android/update/(?P<slug>[\w|\W]+)/$', |
334 | + IntegrationLoopUpdateView.as_view(), name='AndroidLoopUpdate'), |
335 | +) |
336 | |
337 | === added directory 'dashboard/frontend/android_build/views' |
338 | === added file 'dashboard/frontend/android_build/views/__init__.py' |
339 | === added directory 'dashboard/frontend/integration_loop' |
340 | === added file 'dashboard/frontend/integration_loop/__init__.py' |
341 | === added directory 'dashboard/frontend/integration_loop/forms' |
342 | === added file 'dashboard/frontend/integration_loop/forms/__init__.py' |
343 | === renamed file 'dashboard/frontend/forms/integration_loop_form.py' => 'dashboard/frontend/integration_loop/forms/integration_loop_form.py' |
344 | --- dashboard/frontend/forms/integration_loop_form.py 2012-07-24 15:15:35 +0000 |
345 | +++ dashboard/frontend/integration_loop/forms/integration_loop_form.py 2012-08-17 07:43:18 +0000 |
346 | @@ -17,7 +17,7 @@ |
347 | # along with linaro-ci-dashboard. If not, see <http://www.gnu.org/licenses/>. |
348 | |
349 | from django.forms import ModelForm |
350 | -from frontend.models.integration_loop import IntegrationLoop |
351 | +from frontend.integration_loop.models.integration_loop import IntegrationLoop |
352 | |
353 | |
354 | class IntegrationLoopForm(ModelForm): |
355 | |
356 | === added directory 'dashboard/frontend/integration_loop/migrations' |
357 | === added file 'dashboard/frontend/integration_loop/migrations/0001_initial.py' |
358 | --- dashboard/frontend/integration_loop/migrations/0001_initial.py 1970-01-01 00:00:00 +0000 |
359 | +++ dashboard/frontend/integration_loop/migrations/0001_initial.py 2012-08-17 07:43:18 +0000 |
360 | @@ -0,0 +1,50 @@ |
361 | +# encoding: utf-8 |
362 | +import datetime |
363 | +from south.db import db |
364 | +from south.v2 import SchemaMigration |
365 | +from django.db import models |
366 | + |
367 | +class Migration(SchemaMigration): |
368 | + |
369 | + def forwards(self, orm): |
370 | + |
371 | + # Adding model 'IntegrationLoop' |
372 | + db.create_table('integration_loop_integrationloop', ( |
373 | + ('loop_ptr', self.gf('django.db.models.fields.related.OneToOneField')(to=orm['frontend.Loop'], unique=True, primary_key=True)), |
374 | + ('branch', self.gf('django.db.models.fields.CharField')(max_length=200)), |
375 | + ('precommand', self.gf('django.db.models.fields.CharField')(max_length=200)), |
376 | + ('command', self.gf('django.db.models.fields.CharField')(max_length=200)), |
377 | + )) |
378 | + db.send_create_signal('integration_loop', ['IntegrationLoop']) |
379 | + |
380 | + |
381 | + def backwards(self, orm): |
382 | + |
383 | + # Deleting model 'IntegrationLoop' |
384 | + db.delete_table('integration_loop_integrationloop') |
385 | + |
386 | + |
387 | + models = { |
388 | + 'frontend.loop': { |
389 | + 'Meta': {'object_name': 'Loop'}, |
390 | + 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), |
391 | + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '200'}), |
392 | + 'server': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['jenkinsserver.JenkinsServer']"}) |
393 | + }, |
394 | + 'integration_loop.integrationloop': { |
395 | + 'Meta': {'object_name': 'IntegrationLoop', '_ormbases': ['frontend.Loop']}, |
396 | + 'branch': ('django.db.models.fields.CharField', [], {'max_length': '200'}), |
397 | + 'command': ('django.db.models.fields.CharField', [], {'max_length': '200'}), |
398 | + 'loop_ptr': ('django.db.models.fields.related.OneToOneField', [], {'to': "orm['frontend.Loop']", 'unique': 'True', 'primary_key': 'True'}), |
399 | + 'precommand': ('django.db.models.fields.CharField', [], {'max_length': '200'}) |
400 | + }, |
401 | + 'jenkinsserver.jenkinsserver': { |
402 | + 'Meta': {'object_name': 'JenkinsServer'}, |
403 | + 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), |
404 | + 'password': ('django.db.models.fields.CharField', [], {'max_length': '100'}), |
405 | + 'url': ('django.db.models.fields.CharField', [], {'max_length': '255'}), |
406 | + 'username': ('django.db.models.fields.CharField', [], {'max_length': '100'}) |
407 | + } |
408 | + } |
409 | + |
410 | + complete_apps = ['integration_loop'] |
411 | |
412 | === added file 'dashboard/frontend/integration_loop/migrations/__init__.py' |
413 | === added directory 'dashboard/frontend/integration_loop/models' |
414 | === added file 'dashboard/frontend/integration_loop/models/__init__.py' |
415 | --- dashboard/frontend/integration_loop/models/__init__.py 1970-01-01 00:00:00 +0000 |
416 | +++ dashboard/frontend/integration_loop/models/__init__.py 2012-08-17 07:43:18 +0000 |
417 | @@ -0,0 +1,1 @@ |
418 | +from frontend.integration_loop.models.integration_loop import IntegrationLoop |
419 | \ No newline at end of file |
420 | |
421 | === renamed file 'dashboard/frontend/models/integration_loop.py' => 'dashboard/frontend/integration_loop/models/integration_loop.py' |
422 | --- dashboard/frontend/models/integration_loop.py 2012-07-26 13:25:06 +0000 |
423 | +++ dashboard/frontend/integration_loop/models/integration_loop.py 2012-08-17 07:43:18 +0000 |
424 | @@ -16,7 +16,6 @@ |
425 | # You should have received a copy of the GNU Affero General Public License |
426 | # along with linaro-ci-dashboard. If not, see <http://www.gnu.org/licenses/>. |
427 | |
428 | -from django.contrib.auth.models import User |
429 | from django.db import models |
430 | from frontend.models.loop import Loop |
431 | from jenkinsserver.models.jenkins_server import JenkinsServer |
432 | @@ -24,7 +23,7 @@ |
433 | |
434 | class IntegrationLoop(Loop): |
435 | class Meta: |
436 | - app_label = 'frontend' |
437 | + app_label = 'integration_loop' |
438 | |
439 | branch = models.CharField(max_length=200) |
440 | precommand = models.CharField(max_length=200) |
441 | |
442 | === added directory 'dashboard/frontend/integration_loop/templates' |
443 | === added file 'dashboard/frontend/integration_loop/templates/__init__.py' |
444 | === renamed file 'dashboard/frontend/templates/integration_loop_create.html' => 'dashboard/frontend/integration_loop/templates/integration_loop_create.html' |
445 | === renamed file 'dashboard/frontend/templates/integration_loop_detail.html' => 'dashboard/frontend/integration_loop/templates/integration_loop_detail.html' |
446 | === renamed file 'dashboard/frontend/templates/integration_loop_update.html' => 'dashboard/frontend/integration_loop/templates/integration_loop_update.html' |
447 | === added file 'dashboard/frontend/integration_loop/urls.py' |
448 | --- dashboard/frontend/integration_loop/urls.py 1970-01-01 00:00:00 +0000 |
449 | +++ dashboard/frontend/integration_loop/urls.py 2012-08-17 07:43:18 +0000 |
450 | @@ -0,0 +1,34 @@ |
451 | +# Copyright (C) 2012 Linaro |
452 | +# |
453 | +# This file is part of linaro-ci-dashboard. |
454 | +# |
455 | +# linaro-ci-dashboard is free software: you can redistribute it and/or modify |
456 | +# it under the terms of the GNU Affero General Public License as published by |
457 | +# the Free Software Foundation, either version 3 of the License, or |
458 | +# (at your option) any later version. |
459 | +# |
460 | +# linaro-ci-dashboard is distributed in the hope that it will be useful, |
461 | +# but WITHOUT ANY WARRANTY; without even the implied warranty of |
462 | +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
463 | +# GNU Affero General Public License for more details. |
464 | +# |
465 | +# You should have received a copy of the GNU Affero General Public License |
466 | +# along with linaro-ci-dashboard. If not, see <http://www.gnu.org/licenses/>. |
467 | + |
468 | +from django.conf.urls.defaults import patterns, include, url |
469 | +from frontend.integration_loop.views.integration_loop_create_view\ |
470 | + import IntegrationLoopCreateView |
471 | +from frontend.integration_loop.views.integration_loop_update_view\ |
472 | + import IntegrationLoopUpdateView |
473 | +from frontend.integration_loop.views.integration_loop_detail_view\ |
474 | + import IntegrationLoopDetailView |
475 | + |
476 | + |
477 | +urlpatterns = patterns('', |
478 | + url(r'^integration_loop/create/$', |
479 | + IntegrationLoopCreateView.as_view(), name='IntegrationLoopCreate'), |
480 | + url(r'^integration_loop/detail/(?P<slug>[\w|\W]+)/$', |
481 | + IntegrationLoopDetailView.as_view(), name='IntegrationLoopDetail'), |
482 | + url(r'^integration_loop/update/(?P<slug>[\w|\W]+)/$', |
483 | + IntegrationLoopUpdateView.as_view(), name='IntegrationLoopUpdate'), |
484 | +) |
485 | |
486 | === added directory 'dashboard/frontend/integration_loop/views' |
487 | === added file 'dashboard/frontend/integration_loop/views/__init__.py' |
488 | === renamed file 'dashboard/frontend/views/integration_loop_create_view.py' => 'dashboard/frontend/integration_loop/views/integration_loop_create_view.py' |
489 | --- dashboard/frontend/views/integration_loop_create_view.py 2012-07-26 13:25:06 +0000 |
490 | +++ dashboard/frontend/integration_loop/views/integration_loop_create_view.py 2012-08-17 07:43:18 +0000 |
491 | @@ -18,11 +18,11 @@ |
492 | |
493 | from django.contrib.auth.decorators import login_required |
494 | from django.core.urlresolvers import reverse |
495 | -from django.http import HttpResponseRedirect |
496 | from django.views.generic.edit import CreateView |
497 | from django.utils.decorators import method_decorator |
498 | -from frontend.forms.integration_loop_form import IntegrationLoopForm |
499 | -from frontend.models.integration_loop import IntegrationLoop |
500 | +from frontend.integration_loop.forms.integration_loop_form \ |
501 | + import IntegrationLoopForm |
502 | +from frontend.integration_loop.models.integration_loop import IntegrationLoop |
503 | |
504 | |
505 | class IntegrationLoopCreateView(CreateView): |
506 | |
507 | === renamed file 'dashboard/frontend/views/integration_loop_detail_view.py' => 'dashboard/frontend/integration_loop/views/integration_loop_detail_view.py' |
508 | --- dashboard/frontend/views/integration_loop_detail_view.py 2012-07-24 15:15:35 +0000 |
509 | +++ dashboard/frontend/integration_loop/views/integration_loop_detail_view.py 2012-08-17 07:43:18 +0000 |
510 | @@ -19,7 +19,7 @@ |
511 | from django.contrib.auth.decorators import login_required |
512 | from django.views.generic.detail import DetailView |
513 | from django.utils.decorators import method_decorator |
514 | -from frontend.models.integration_loop import IntegrationLoop |
515 | +from frontend.integration_loop.models.integration_loop import IntegrationLoop |
516 | |
517 | |
518 | class IntegrationLoopDetailView(DetailView): |
519 | |
520 | === renamed file 'dashboard/frontend/views/integration_loop_update_view.py' => 'dashboard/frontend/integration_loop/views/integration_loop_update_view.py' |
521 | --- dashboard/frontend/views/integration_loop_update_view.py 2012-07-26 13:25:06 +0000 |
522 | +++ dashboard/frontend/integration_loop/views/integration_loop_update_view.py 2012-08-17 07:43:18 +0000 |
523 | @@ -18,11 +18,11 @@ |
524 | |
525 | from django.contrib.auth.decorators import login_required |
526 | from django.core.urlresolvers import reverse |
527 | -from django.http import HttpResponseRedirect |
528 | from django.views.generic.edit import UpdateView |
529 | from django.utils.decorators import method_decorator |
530 | -from frontend.forms.integration_loop_form import IntegrationLoopForm |
531 | -from frontend.models.integration_loop import IntegrationLoop |
532 | +from frontend.integration_loop.forms.integration_loop_form \ |
533 | + import IntegrationLoopForm |
534 | +from frontend.integration_loop.models.integration_loop import IntegrationLoop |
535 | |
536 | |
537 | class IntegrationLoopUpdateView(UpdateView): |
538 | |
539 | === modified file 'dashboard/frontend/migrations/0001_initial.py' |
540 | --- dashboard/frontend/migrations/0001_initial.py 2012-07-25 12:20:01 +0000 |
541 | +++ dashboard/frontend/migrations/0001_initial.py 2012-08-17 07:43:18 +0000 |
542 | @@ -16,15 +16,6 @@ |
543 | )) |
544 | db.send_create_signal('frontend', ['Loop']) |
545 | |
546 | - # Adding model 'IntegrationLoop' |
547 | - db.create_table('frontend_integrationloop', ( |
548 | - ('loop_ptr', self.gf('django.db.models.fields.related.OneToOneField')(to=orm['frontend.Loop'], unique=True, primary_key=True)), |
549 | - ('branch', self.gf('django.db.models.fields.CharField')(max_length=200)), |
550 | - ('precommand', self.gf('django.db.models.fields.CharField')(max_length=200)), |
551 | - ('command', self.gf('django.db.models.fields.CharField')(max_length=200)), |
552 | - )) |
553 | - db.send_create_signal('frontend', ['IntegrationLoop']) |
554 | - |
555 | # Adding model 'LoopBuild' |
556 | db.create_table('frontend_loopbuild', ( |
557 | ('id', self.gf('django.db.models.fields.AutoField')(primary_key=True)), |
558 | @@ -42,21 +33,11 @@ |
559 | # Deleting model 'Loop' |
560 | db.delete_table('frontend_loop') |
561 | |
562 | - # Deleting model 'IntegrationLoop' |
563 | - db.delete_table('frontend_integrationloop') |
564 | - |
565 | # Deleting model 'LoopBuild' |
566 | db.delete_table('frontend_loopbuild') |
567 | |
568 | |
569 | models = { |
570 | - 'frontend.integrationloop': { |
571 | - 'Meta': {'object_name': 'IntegrationLoop', '_ormbases': ['frontend.Loop']}, |
572 | - 'branch': ('django.db.models.fields.CharField', [], {'max_length': '200'}), |
573 | - 'command': ('django.db.models.fields.CharField', [], {'max_length': '200'}), |
574 | - 'loop_ptr': ('django.db.models.fields.related.OneToOneField', [], {'to': "orm['frontend.Loop']", 'unique': 'True', 'primary_key': 'True'}), |
575 | - 'precommand': ('django.db.models.fields.CharField', [], {'max_length': '200'}) |
576 | - }, |
577 | 'frontend.loop': { |
578 | 'Meta': {'object_name': 'Loop'}, |
579 | 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), |
580 | |
581 | === modified file 'dashboard/frontend/models/__init__.py' |
582 | --- dashboard/frontend/models/__init__.py 2012-07-24 15:15:35 +0000 |
583 | +++ dashboard/frontend/models/__init__.py 2012-08-17 07:43:18 +0000 |
584 | @@ -1,3 +1,2 @@ |
585 | from frontend.models.loop import Loop |
586 | -from frontend.models.integration_loop import IntegrationLoop |
587 | from frontend.models.loop_build import LoopBuild |
588 | |
589 | === modified file 'dashboard/frontend/models/loop.py' |
590 | --- dashboard/frontend/models/loop.py 2012-07-26 13:25:06 +0000 |
591 | +++ dashboard/frontend/models/loop.py 2012-08-17 07:43:18 +0000 |
592 | @@ -16,7 +16,6 @@ |
593 | # You should have received a copy of the GNU Affero General Public License |
594 | # along with linaro-ci-dashboard. If not, see <http://www.gnu.org/licenses/>. |
595 | |
596 | -from django.contrib.auth.models import User |
597 | from django.db import models |
598 | from jenkinsserver.models.jenkins_server import JenkinsServer |
599 | |
600 | |
601 | === modified file 'dashboard/frontend/tests/test_views.py' |
602 | --- dashboard/frontend/tests/test_views.py 2012-07-28 02:27:35 +0000 |
603 | +++ dashboard/frontend/tests/test_views.py 2012-08-17 07:43:18 +0000 |
604 | @@ -20,12 +20,12 @@ |
605 | |
606 | from frontend.views.home_page_view import HomePageView |
607 | from frontend.views.index_view import IndexView |
608 | -from frontend.views.integration_loop_create_view \ |
609 | - import IntegrationLoopCreateView |
610 | -from frontend.views.integration_loop_update_view \ |
611 | - import IntegrationLoopUpdateView |
612 | -from frontend.views.integration_loop_detail_view \ |
613 | - import IntegrationLoopDetailView |
614 | +from frontend.integration_loop.views.integration_loop_create_view \ |
615 | + import IntegrationLoopCreateView |
616 | +from frontend.integration_loop.views.integration_loop_update_view \ |
617 | + import IntegrationLoopUpdateView |
618 | +from frontend.integration_loop.views.integration_loop_detail_view \ |
619 | + import IntegrationLoopDetailView |
620 | |
621 | |
622 | class HomePageViewTest(TestCase): |
623 | |
624 | === modified file 'dashboard/frontend/urls.py' |
625 | --- dashboard/frontend/urls.py 2012-07-24 15:29:46 +0000 |
626 | +++ dashboard/frontend/urls.py 2012-08-17 07:43:18 +0000 |
627 | @@ -19,24 +19,13 @@ |
628 | from django.conf.urls.defaults import patterns, include, url |
629 | from frontend.views.home_page_view import HomePageView |
630 | from frontend.views.index_view import IndexView |
631 | -from frontend.views.integration_loop_create_view \ |
632 | - import IntegrationLoopCreateView |
633 | -from frontend.views.integration_loop_update_view \ |
634 | - import IntegrationLoopUpdateView |
635 | -from frontend.views.integration_loop_detail_view \ |
636 | - import IntegrationLoopDetailView |
637 | from frontend.views.loop_build_view import LoopBuildView |
638 | |
639 | + |
640 | urlpatterns = patterns('', |
641 | url(r'^$', IndexView.as_view(), name='Index'), |
642 | url(r'^index/$', IndexView.as_view(), name='Index'), |
643 | url(r'^home/$', HomePageView.as_view(), name='Home'), |
644 | - url(r'^integration_loop/create/$', |
645 | - IntegrationLoopCreateView.as_view(), name='IntegrationLoopCreate'), |
646 | - url(r'^integration_loop/detail/(?P<slug>[\w|\W]+)/$', |
647 | - IntegrationLoopDetailView.as_view(), name='IntegrationLoopDetail'), |
648 | - url(r'^integration_loop/update/(?P<slug>[\w|\W]+)/$', |
649 | - IntegrationLoopUpdateView.as_view(), name='IntegrationLoopUpdate'), |
650 | url(r'^loop/build/(?P<slug>[\w|\W]+)/$', |
651 | LoopBuildView.as_view(), name='LoopBuild'), |
652 | ) |
653 | |
654 | === modified file 'dashboard/frontend/views/index_view.py' |
655 | --- dashboard/frontend/views/index_view.py 2012-07-24 15:15:35 +0000 |
656 | +++ dashboard/frontend/views/index_view.py 2012-08-17 07:43:18 +0000 |
657 | @@ -19,7 +19,7 @@ |
658 | from django.views.generic.base import TemplateView |
659 | from django.utils.decorators import method_decorator |
660 | from django.contrib.auth.decorators import login_required |
661 | -from frontend.models.integration_loop import IntegrationLoop |
662 | +from frontend.integration_loop.models.integration_loop import IntegrationLoop |
663 | |
664 | |
665 | class IndexView(TemplateView): |
666 | |
667 | === modified file 'dashboard/frontend/views/loop_build_view.py' |
668 | --- dashboard/frontend/views/loop_build_view.py 2012-07-20 11:00:36 +0000 |
669 | +++ dashboard/frontend/views/loop_build_view.py 2012-08-17 07:43:18 +0000 |
670 | @@ -17,8 +17,6 @@ |
671 | # along with linaro-ci-dashboard. If not, see <http://www.gnu.org/licenses/>. |
672 | |
673 | from django.contrib.auth.decorators import login_required |
674 | -from django.core import serializers |
675 | -from django.views.generic import View |
676 | from django.views.generic.detail import DetailView |
677 | from django.utils.decorators import method_decorator |
678 | from frontend.models.loop import Loop |
679 | |
680 | === modified file 'dashboard/settings.py' |
681 | --- dashboard/settings.py 2012-07-24 21:28:00 +0000 |
682 | +++ dashboard/settings.py 2012-08-17 07:43:18 +0000 |
683 | @@ -44,6 +44,7 @@ |
684 | } |
685 | |
686 | SOUTH_TESTS_MIGRATE = False |
687 | +SKIP_SOUTH_TESTS = True |
688 | |
689 | # Local time zone for this installation. Choices can be found here: |
690 | # http://en.wikipedia.org/wiki/List_of_tz_zones_by_name |
691 | @@ -139,6 +140,8 @@ |
692 | 'django_openid_auth', |
693 | 'jenkinsserver', |
694 | 'frontend', |
695 | + 'frontend.android_build', |
696 | + 'frontend.integration_loop', |
697 | 'south', |
698 | # Uncomment the next line to enable the admin: |
699 | # 'django.contrib.admin', |
700 | |
701 | === modified file 'dashboard/urls.py' |
702 | --- dashboard/urls.py 2012-07-19 19:58:21 +0000 |
703 | +++ dashboard/urls.py 2012-08-17 07:43:18 +0000 |
704 | @@ -30,4 +30,6 @@ |
705 | url(r'^js/(?P<path>.*)$', 'django.views.static.serve', |
706 | {'document_root': settings.JS_PATH}), |
707 | url(r'^', include('dashboard.frontend.urls')), |
708 | + url(r'^', include('dashboard.frontend.android_build.urls')), |
709 | + url(r'^', include('dashboard.frontend.integration_loop.urls')), |
710 | ) |
The starting steps look good.