Skip to main content
aboutsummaryrefslogtreecommitdiffstats
blob: 4c24758e7b8e482a6c1be2687f2e11133809453d (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
/*****************************************************************************
 * Copyright (c) 2014, 2016 Cedric Dumoulin, Christian W. Damus, and others.
 *    
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 *
 * Contributors:
 *  Cedric Dumoulin  Cedric.dumoulin@lifl.fr - Initial API and implementation
 *  Christian W. Damus - bug 485220
 *
 *****************************************************************************/

package org.eclipse.papyrus.uml.profile.drafter.model;

import java.util.Collections;
import java.util.Map;

import org.eclipse.emf.common.util.URI;
import org.eclipse.emf.ecore.EObject;
import org.eclipse.emf.ecore.resource.Resource;
import org.eclipse.emf.ecore.resource.URIConverter;
import org.eclipse.papyrus.infra.core.resource.EMFLogicalModel;
import org.eclipse.papyrus.infra.core.resource.IModel;
import org.eclipse.papyrus.infra.core.resource.ModelSet;
import org.eclipse.uml2.uml.Profile;
import org.eclipse.uml2.uml.UMLFactory;
import org.eclipse.uml2.uml.UMLPackage;

/**
 * A {@link ModelSet}'s {@link IModel} dedicated to created {@link Profile}.
 * <br>
 * Such {@link IModel} contains the created {@link Profile}, and can be managed by Papyrus {@link ModelSet}.
 * The model encapsulate 3 {@link Resource}s: one for uml, one for diagram, and one for di.
 * <br>
 * This implementation try to load the {@link Resource}s asociated to the requested URI. If existing resources are found,
 * load them. Otherwise, create them.
 * 
 * @author cedric dumoulin
 *
 */
public class CreatedPapyrusProfileModel extends EMFLogicalModel {

	/**
	 * File extension used for DI.
	 */
	public static final String UML_FILE_EXTENSION = "uml"; //$NON-NLS-1$

	/**
	 * Model ID.
	 * We use the class qualified name.
	 */
	public static final String MODEL_ID = CreatedPapyrusProfileModel.class.getName();

	public static final String PROFILE_FILE_EXTENSION = "profile";

	protected URI uriWithoutExtension;
	protected boolean isAdditionalResourcesRequired;
	protected Resource umlResource;
	protected Resource diResource;
	protected Resource notationResource;


	/**
	 * 
	 * Constructor.
	 *
	 * @param owner
	 * @param uriWithoutExtension
	 * @param isAdditionalResourcesRequired
	 */
	public CreatedPapyrusProfileModel(ModelSet owner, URI uriWithoutExtension, boolean isAdditionalResourcesRequired) {
		init(owner);
		this.uriWithoutExtension = uriWithoutExtension;
		this.isAdditionalResourcesRequired = isAdditionalResourcesRequired;

		// add '.profile' to uri if needed
		String currentExtension = uriWithoutExtension.fileExtension();
		if (!PROFILE_FILE_EXTENSION.equals(currentExtension)) {
			// Add extension
			uriWithoutExtension.appendFileExtension(PROFILE_FILE_EXTENSION);
		}

		// Creates Resources
		createModel();
		// Register ourself to ModelSet
		owner.registerModel(this);
	}

	/**
	 * Use the uri.toString has identifier.
	 * 
	 * @see org.eclipse.papyrus.infra.core.resource.AbstractModel#getIdentifier()
	 *
	 * @return
	 */
	@Override
	public String getIdentifier() {
		return uriWithoutExtension.toString();
	}

	/**
	 * 
	 * @see org.eclipse.papyrus.infra.core.resource.AbstractBaseModel#getModelFileExtension()
	 *
	 * @return
	 */
	@Override
	protected String getModelFileExtension() {
		// TODO Auto-generated method stub
		return UML_FILE_EXTENSION;
	}

	/**
	 * Create the model by using the provided fullpath as a hint for the resource
	 * URIs.
	 * In this implementation, create 3 resources (profile.uml, di and notation).
	 * 
	 * @param fullPathWithoutExtension
	 */
	public void createModel() {


		umlResource = createUmlResource();
		// Initialize resource
		if (umlResource.getContents().isEmpty()) {
			Profile profile = createProfile();
			umlResource.getContents().add(profile);
		}

		// Set the main resource
		resource = umlResource;

		// Add additional resources if requested.
		if (isAdditionalResourcesRequired) {
			notationResource = createNotationResource();
			diResource = createDiResource();
		}


	}

	/**
	 * Create
	 * 
	 * @param uriWithoutExtension2
	 * @return
	 */
	private Resource createUmlResource() {
		umlResource = createResource(uriWithoutExtension.appendFileExtension("uml"));
		// init model

		return umlResource;
	}

	private Resource createNotationResource() {
		notationResource = createResource(uriWithoutExtension.appendFileExtension("notation"));
		// init model

		return notationResource;
	}

	private Resource createDiResource() {
		diResource = createResource(uriWithoutExtension.appendFileExtension("di"));
		// init model

		return diResource;
	}

	/**
	 * Create the specified Profile
	 * 
	 * @param profileName
	 *            The name of the Profile to create.
	 * 
	 */
	private Profile createProfile() {
		Profile resultProfile = UMLFactory.eINSTANCE.createProfile();
		// resultProfile.setName(profileName);

		return resultProfile;
	}

	/**
	 * Get or Create the specified Resource
	 * 
	 * @param resourceURI
	 *            URI of the {@link Resource} that should be created.
	 * @return The requested Resource with specified URI.
	 */
	protected Resource createResource(URI resourceURI) {

		// Create Resource of appropriate type
		ModelSet modelSet = getModelManager();
		Resource resource = modelSet.getResource(resourceURI, false);
		if (resource != null) {
			// it already exists? Best effort to make sure it's loaded
			try {
				modelSet.getResource(resourceURI, true);
			} catch (RuntimeException e) {
				// it commonly happens when creating a new model in the
				// workspace that the wizard creates an empty file, first.
				Map<String, ?> attributes = modelSet.getURIConverter().getAttributes(resourceURI, Collections.singletonMap(URIConverter.OPTION_REQUESTED_ATTRIBUTES, Collections.singleton(URIConverter.ATTRIBUTE_LENGTH)));
				Number length = (Number) attributes.get(URIConverter.ATTRIBUTE_LENGTH);
				if ((length != null) && (length.longValue() > 0L)) {
					// it has some length but isn't readable; fail
					throw e;
				} // otherwise, it's just empty and we'll fill it
			}
		} else {
			// new resource
			resource = getModelManager().createResource(resourceURI);
		}
		configureResource(resource);
		return resource;
	}

	/**
	 * Return true if the specified resource is related to the main resource.
	 * In this class, the resource is related if the fullpathname without extension is the same as the main resource.
	 * 
	 * @see org.eclipse.papyrus.infra.core.resource.EMFLogicalModel#isRelatedResource(org.eclipse.emf.ecore.resource.Resource)
	 *
	 * @param resource
	 * @return
	 */
	@Override
	protected boolean isRelatedResource(Resource resource) {
		if (resource == null) {
			return false;
		}

		return resource.getURI().trimFileExtension().equals(uriWithoutExtension);
	}

	/**
	 * 
	 * @return
	 */
	public Profile getProfile() {
		return (Profile) umlResource.getContents().get(0);
	}

	/**
	 * 
	 * @return
	 */
	public Resource getProfileResource() {
		return umlResource;
	}

	@Override
	protected boolean isRootElement(EObject object) {
		return super.isRootElement(object) && (object instanceof Profile);
	}

	@Override
	protected boolean isSupportedRoot(EObject object) {
		return UMLPackage.Literals.PROFILE.isInstance(object);
	}
}

Back to the top