I have an non-persistent attribute (SITEID) on my WOCHANGE object that originates from the parent object, WORKORDER. For some particular reason, this attribute has a few problems that I've never really seen with other attributes before.
Based on various configurations I have tried in an attempt to remedy the issue, here are the main issues:
It doesn't trigger the WOCHANGE to save when changed.
In addition to the value not being saved, I can change the value on one record, go to another and the value persists on the different record.
The field is readonly unless I define it to have an inputmode of DEFAULT. This is odd to me, because not defining inputmode usually implies default behavior (NOT readonly).
Here are the definitions for the SITEID attribute on both the WORKORDER
and WOCHANGE objects.
SITEID also uses a TABLE domain belonging to the SITE table.
Are there any attribute rules being applied from other sources that I should be checking?
That workorder field class on there may not be desired and may be messing with things, like setting the field to read-only. Site Id is commonly a read-only field, especially when the record is no longer a new record. Because of that, the logic to make that field read-only could be buried deeper in the Maximo business logic than just that field class. You are working with a field that has a lot of special meaning in Maximo, you are likely going to stumble into many built-in business rules.
Since non-persistent fields are not saved in the database (they are in memory fields only), I don't believe they trigger the flag for a record to be saved. What would be saved? Nothing in the database (a save) is to be changed yet.
Your screenshot however shows the field as persistent. Is WOCHANGE a view? I can't recall and no longer have the resources to check.
Related
I am a bit confused how to use the component <sw-entity-multi-select>. I understand that the difference between this component and the <sw-entity-multi-id-select> is that the first one returns the entities and the latter one returns just the id of the selected entities. But from the structure and the props they are totally different.
I am confused, because I mainly use the component as this:
<sw-entity-multi-select
entityName="language"
:entity-collection="languages"
:criteria="salesChannelLanguageCriteria"
:label="Language"
#change="selectLanguage"
>
</sw-entity-multi-select>
I could remove the entityName here, as the name is retrieved from the collection as well. But when I dig into the core, I see that inside selectLanguage I should do this:
selectLanguage(languages) {
this.languageIds = languages.getIds();
this.languages = languages;
}
I now understand that languageIds are kind of the v-model that determine, which entities should be selected in the component. Is this true? Why do I have to set the this.languages here again then? To me it's kind of magic if languageIds have this role here, because it's not referenced anywhere on the component. How does it work and how do I tell the component which items are selected - is using languageIds the correct way?
I now understand that languageIds are kind of the v-model that determine, which entities should be selected in the component. Is this true?
No. This example probably just extracts the IDs for some other use, e.g. for adding associations of language to another entity. One could arguably that if this is the only purpose of the selection sw-entity-multi-id-select might be the better component to use.
Why do I have to set the this.languages here again then?
Because you want to store the updated entity collection to persist the selection. Whatever is selected within the multi select is derived from that collection. So, let's say, initially you start out with an empty entity collection. You select some entities and the change is emitted with the updated collection containing the selected entities. Given we have :entity-collection="languages" we then want this.languages to be this updated collection, so the selection persists. So we kinda complete a loop here.
On another note, you could also use the collection with v-model="languages". In that case any additions or removals within the selection would be applied reactively to the collection and you wouldn't need to set this.languages after each change and you could also remove :entity-collection="languages". So basically, which of these approaches you use depends on whether you want your changes applied reactively or not.
I am facing an issue with extended attributes on a document (trying to extend a document table). I created the original table’s PK (FDOC_NBR) in the extended table and linked the two via a foreignKey of the customized original table’s ojb entry (as an “extension” reference-descriptor). I created the bo and dd for the extension and customized the original document’s dd to add the new attributes. On the extended BO itself I also added members (with setters and getters) for the 2 new columns + for the PK column of documentNumber. I also added the new attributes to the documet’s jsp. The pertinent module definition was already extended to include custom dd, ojb, etc. files.
Indeed, when opening the document the new fields are shown- however, when trying to submit the document (regardless of doing anything with the new fields) I get an error-
Error Details: OJB operation; SQL []; ORA-01400: cannot insert NULL
into ("KFSTEM"."TEM_TRVL_ARRANGER_DOC_EXT_T"."FDOC_NBR") ; nested
exception is java.sql.SQLIntegrityConstraintViolationException:
ORA-01400: cannot insert NULL into
("KFSTEM"."TEM_TRVL_ARRANGER_DOC_EXT_T"."FDOC_NBR")
Seems like somehow the system tries to insert a value of NULL into the extension’s PK field, instead of the actual document number. Trying to debug this, in the action’s route method and all the way down to DocumentDaoOjb.save (which is as far down as I can go) I see the document with the real doc number is passed on, so the problem seems to be purely with ojb trying to set this number to the extension table.
Does anyone have any experience with extended attributes on documents that could help shed some light on this?
KFS is using the KNS, and in the Kuali Nervous System, the primary key on the extended attributes object must be set through manual intervention.
In this case, it looks as if you're adding an extended attribute to a transactional document, the Travel Arranger document (TAA), which simplifies things. Basically, you'll need to extend org.kuali.kfs.module.tem.document.TravelArrangerDocument and override prepareForSave to set the document number there (it may be set already since prepareForSave should be called several times during the routing process, but there's no real harm from overwriting that information as the base document's number will remain the same).
Hope this helps!
I have a strange thing, I'm using dynamic field binding in a custom control.
The field binding is created like this.
XPage (Datasource "document" is placed here)
Custom Control (String passed in)
(to get errors if there are any)
Repeat (CompositeData is passed to a bean that returns the strings for Rows,columns)
Repeat (repeat 1 variable used for Columns)
Custom Control (fieldname is passed in)
field binding is done like this
#{document[compositeData.fieldName]}
The problem is that when I save the XPage I get an error in the messages control
Document has been saved by another user - Save created a new document as a response to that modified document.
And all fields are cleared.
Any ideas how to debug this or is there something I'm missing?
The "Document has been saved by another user" error is only tip of the iceberg - there are some really strange problems with reapeats that repeats fields that are bound and repeatControls property is set to false. The decoding part of xpages lifecycle cannot handle it properly - the controls will be losing data. You should use repeatControls set to true as Martin suggests.
"Repeat control variable doesn't exists" is probably caused by the property that removes repeats set to true. You can solve this by either changing it to false or by adding additional data context that will keep repeated value.
And finally for this to have add/remove functionality You can use Dynamic Content Control and show(null) hack to rebuild the repeat content.
To manage this complexity better I would advise You to stop using document data source and start creating some managed beans.
If You will follow my suggestions I guarantee that You will get the functionality You are looking for as I have few apps that works great and have this kind of complex data editors in them.
I don't know if it'll help you, but I pass both the document datasource and the field name as parameters to a DynamicField control, and use it like this:
compositeData.dataSource[compositeData.fieldName]
The type of the datasource is com.ibm.xsp.model.DataSource, it's listed as dataInterface under Data Sources.
Do you have repeatControls="true" set for the repeat control?
It sounds like you've got the datasource defined multiple times on the XPage (plus custom controls). Either that or the save button has save="true" but the code saves the document back-end, or code in multiple places saves the same document. I've used the same method of passing the datasource down to the custom control, but that may just be because that was what I saw on a blog.
I am designing an application that will display dynamically-generated forms to the user who will then enter values into the form fields and submit those values for persistence. The form represents an employee evaluation.
One use case allows an administrator (from HR) to define the form fields. They should be able to create a new form, add/remove fields from a form and mark a form as 'deleted'.
The second use case is when a manager views the form and enters values into the form fields for a specific employee. They should be able to save the values at any time and recall the saved values when viewing the form again for the same employee.
Finally, when the manager is satisfied with the values they've entered for that employee, they can 'submit' the form data which persists the flattened data into the data warehouse for reporting purposes. When this is done, the 'working' copy of the data is removed so the form will display empty the next time they view it for that employee.
I am not concerned with the front-end at this point and working on the back-end service application that sits between the client and the data store. The application must provide a course-grained interface for all of the behavior required.
My question is how many aggregate roots do I actually have (and from that, how many repositories, etc)? Do I separate the form definition from the form data even though I need both when displaying the form to the user?
I see two main entities, 'EmployeeEvaluationSchema' and 'EmployeeEvaluation'. The 'EmployeeEvaluationSchema' entity would have a collection of 'FieldDefinition' value objects which would contain the properties that define a field, the most basic being the name of the field. The 'EmployeeEvaluation' entity would have a collection of 'FieldValue' value objects which contain the values for each field from the definition. In the simplest case, it would have a field name and value property. Next, the 'EmployeeEvaluation' could have a reference to 'EmployeeEvaluationSchema' to specify which definition the particular evaluation is based on. This can also be used to enforce the form definition in each evaluation. You would have two repositories - one for each entity. If you were to use an ORM such as NHibernate, then when you retrieve a 'EmployeeEvaluation' entity, the associated 'EmployeeEvaluationSchema' would also be retrieved even though there is a dedicated repository for it.
From your description it sounds like your objects don't have any behavior and are simple DTOs. If that is the case maybe you should not bother doing DDD. Can you imagine your entities without having getters? There are better ways to do CRUDish application than DDD. Again this is only valid if your "domain" does not have relevant behavior.
This question covncerns my lack of understanding of how to use the core data undo manager and how to restore a NSManagedObject to its state before editing was done.
I am just learning my way around Core Data. I have my NSManagedObject classes set up with their dynamic accessors. I perform a fetch that returns several NSManagedObject entity results. Content from each of these entity results (first name, last name) get put into a table view, and then the user picks one out of the table for detailed view and then editing.
The detail view controller receives a pointer to the selected NSManagedObject entity. As the user edits the fields, the corresponding property value in the NSManagedObject entity is updated. This seemed like the cleanest way to manage these changes.
Now, rather than committing the changes using save, I want to provide a cancel-editing feature that rolls back to what is in the data base for that entity. I really only want to restore the one entity and not perform the entire refetch.
I tried rollback and I tried NSUndoManager (with beginUndoGrouping and endUndoGrouping), and that is not working. I don't think I understand what rollback is really supposed to do.
But in any case, I still want to restore the property values in just that single entity (taking the lazy approach to only fetch what is needed, which is the one entity) so that my detail view controller can refill its view with the correct information. Right now it is using the NSManagedObject entity values, which contain the edited values, which were cancelled.
I suppose I could just start the edit process by creating a copy of the NSManagedObject. If the cancel-editing button is pressed, I could copy it back into the original. (I might even be able to just replace the original with the copy by moving the pointer. But since the pointer has actually been passed through several objects, I'm not sure how to manage the retain number on the copy.)
Does anyone have any other suggestions?
Thanks
Using rollback should accomplish what you want and I'm not sure what it doesn't. It is probably an implementation detail error.
You can find the specific managed object/s that were updated but not yet saved by calling the context's updatedObjects.