I have a simple entity class and it is supposed to include unique names on it.
#Entity
class Package {
#PrimaryKey(sequence = "ID")
public Long id;
#SecondaryKey(relate = Relationship.ONE_TO_ONE)
public String name;
private Package() {}
public Package(String name) { this.name = name; }
#Override
public String toString() { return id + " : " + name; }
}
I want to use deferred writing option because of extensive modification. Here is the test i tried and its output.
final String dbfilename = "test01";
new File(dbfilename).mkdirs();
EnvironmentConfig config = new EnvironmentConfig().setAllowCreate(true);
Environment environment = new Environment(new File(dbfilename), config);
StoreConfig storeConfig = new StoreConfig().setAllowCreate(true).setDeferredWrite(true);
EntityStore store = new EntityStore(environment, "", storeConfig);
PrimaryIndex<Long, Package> primaryIndex = store.getPrimaryIndex(Long.class, Package.class);
try {
primaryIndex.put(new Package("package01")); // will be put.
primaryIndex.put(new Package("package01")); // throws exception.
} catch (UniqueConstraintException ex) {
System.out.println(ex.getMessage());
}
store.sync(); // flush them all
// expecting to find one element
SortedMap<Long,Package> sortedMap = primaryIndex.sortedMap();
for (Package entity : sortedMap.values()) {
System.out.println(entity);
}
Output
(JE 5.0.73) Unique secondary key is already present
1 : package01
2 : package01
So my question is that even if it throws exception while putting second package, why does it lists two packages. Any way to avoid this without using transactions?
Thanks.
Related
I tried to rebuild the sample from the XDocReport documentation, but when i try to create tables or fill them. It always fails due to the follwing error. I cannot figure out what the issue is...
I have updated all the dependencies and tried different syntax in the .odt file.
ERROR:
Apr. 12, 2022 10:21:05 VORM. freemarker.log._JULLoggerFactory$JULLogger error
SEVERE: Error executing FreeMarker template
FreeMarker template error:
The following has evaluated to null or missing:
==> devs.name [in template "fr.opensagres.xdocreport.document.odt.ODTReport#57855c9a!content.xml" at line 5, column 11]
----
Tip: It's the step after the last dot that caused this error, not those before it.
----
Tip: If the failing expression is known to legally refer to something that's sometimes null or missing, either specify a default value like myOptionalVar!myDefault, or use [#if myOptionalVar??]when-present[#else]when-missing[/#if]. (These only cover the last step of the expression; to cover the whole expression, use parenthesis: (myOptionalVar.foo)!myDefault, (myOptionalVar.foo)??
----
----
FTL stack trace ("~" means nesting-related):
- Failed at: ${devs.name} auto-escaped [in template "fr.opensagres.xdocreport.document.odt.ODTReport#57855c9a!content.xml" at line 5, column 9]
----
Java stack trace (for programmers):
----
freemarker.core.InvalidReferenceException: [... Exception message was already printed; see it above ...]
at freemarker.core.InvalidReferenceException.getInstance(InvalidReferenceException.java:134)
at freemarker.core.EvalUtil.coerceModelToTextualCommon(EvalUtil.java:481)
at freemarker.core.EvalUtil.coerceModelToStringOrMarkup(EvalUtil.java:401)
at freemarker.core.EvalUtil.coerceModelToStringOrMarkup(EvalUtil.java:370)
at freemarker.core.BuiltInForLegacyEscaping._eval(BuiltInForLegacyEscaping.java:34)
at freemarker.core.Expression.eval(Expression.java:101)
at freemarker.core.Expression.evalAndCoerceToStringOrUnsupportedMarkup(Expression.java:139)
at freemarker.core.BuiltInForString.getTargetString(BuiltInForString.java:34)
at freemarker.core.BuiltInForString._eval(BuiltInForString.java:29)
at freemarker.core.Expression.eval(Expression.java:101)
at freemarker.core.MethodCall._eval(MethodCall.java:55)
at freemarker.core.Expression.eval(Expression.java:101)
at freemarker.core.Expression.evalAndCoerceToStringOrUnsupportedMarkup(Expression.java:139)
at freemarker.core.BuiltInForString.getTargetString(BuiltInForString.java:34)
at freemarker.core.BuiltInForString._eval(BuiltInForString.java:29)
at freemarker.core.Expression.eval(Expression.java:101)
at freemarker.core.MethodCall._eval(MethodCall.java:55)
at freemarker.core.Expression.eval(Expression.java:101)
at freemarker.core.Expression.evalAndCoerceToStringOrUnsupportedMarkup(Expression.java:139)
at freemarker.core.BuiltInForString.getTargetString(BuiltInForString.java:34)
at freemarker.core.BuiltInForString._eval(BuiltInForString.java:29)
at freemarker.core.Expression.eval(Expression.java:101)
at freemarker.core.MethodCall._eval(MethodCall.java:55)
at freemarker.core.Expression.eval(Expression.java:101)
at freemarker.core.DollarVariable.calculateInterpolatedStringOrMarkup(DollarVariable.java:100)
at freemarker.core.DollarVariable.accept(DollarVariable.java:63)
at freemarker.core.Environment.visit(Environment.java:383)
at freemarker.core.IteratorBlock$IterationContext.executedNestedContentForCollOrSeqListing(IteratorBlock.java:321)
at freemarker.core.IteratorBlock$IterationContext.executeNestedContent(IteratorBlock.java:271)
at freemarker.core.IteratorBlock$IterationContext.accept(IteratorBlock.java:244)
at freemarker.core.Environment.visitIteratorBlock(Environment.java:657)
at freemarker.core.IteratorBlock.acceptWithResult(IteratorBlock.java:108)
at freemarker.core.IteratorBlock.accept(IteratorBlock.java:94)
at freemarker.core.Environment.visit(Environment.java:347)
at freemarker.core.Environment.visit(Environment.java:353)
at freemarker.core.Environment.visit(Environment.java:353)
at freemarker.core.Environment.process(Environment.java:326)
at fr.opensagres.xdocreport.template.freemarker.FreemarkerTemplateEngine.process(FreemarkerTemplateEngine.java:163)
at fr.opensagres.xdocreport.template.freemarker.FreemarkerTemplateEngine.processNoCache(FreemarkerTemplateEngine.java:122)
at fr.opensagres.xdocreport.template.AbstractTemplateEngine.process(AbstractTemplateEngine.java:118)
at fr.opensagres.xdocreport.template.AbstractTemplateEngine.process(AbstractTemplateEngine.java:83)
at fr.opensagres.xdocreport.document.AbstractXDocReport.processTemplateEngine(AbstractXDocReport.java:772)
at fr.opensagres.xdocreport.document.AbstractXDocReport.process(AbstractXDocReport.java:518)
at fr.opensagres.xdocreport.document.AbstractXDocReport.process(AbstractXDocReport.java:484)
at report_creation.fillList.main(fillList.java:51)
I am currently using this code:
fillList.java
public class fillList {
public static void main(String[] args) {
try {
// 1) Load ODT file by filling Velocity template engine and cache
// it to the registry
InputStream in = fillList.class.getResourceAsStream("Test.odt");
IXDocReport report = XDocReportRegistry.getRegistry().loadReport(in, TemplateEngineKind.Freemarker);
// 2) Create fields metadata to manage lazy loop (#foreach velocity)
// for table row.
FieldsMetadata metadata = new FieldsMetadata();
metadata.addFieldAsList("developers.name");
metadata.addFieldAsList("developers.lastName");
metadata.addFieldAsList("developers.mail");
report.setFieldsMetadata(metadata);
// 3) Create context Java model
IContext context = report.createContext();
Project project = new Project("Create Dynamic Reports", 101);
context.put("project", project);
// Register developers list
List<Developer> developers = new ArrayList<>();
developers.add(new Developer("ZERR", "Angelo", "angelo.zerr#gmail.com"));
developers.add(new Developer("Leclercq", "Pascal", "pascal.leclercq#gmail.com"));
context.put("developers", developers);
// 4) Generate report by merging Java model with the ODT
OutputStream out = new FileOutputStream(new File("Test2_out.odt"));
report.process(context, out);
System.out.println("Report creation successfully completed!");
} catch (IOException e) {
System.err.println("[Debug Assistent]: No report created! >> IOException");
e.printStackTrace();
} catch (XDocReportException e) {
System.err.println("[Debug Assistent]: No report created! >> XDocReportException");
e.printStackTrace();
}
}
}
Project.java
public class Project {
private final String name;
private final Integer ID;
public Project(String name, Integer id) {
this.name = name;
this.ID = id;
}
public String getName() {
return name;
}
public Integer getID() {
return ID;
}
}
Developer.java
public class Developer {
private final String name;
private final String lastName;
private final String mail;
public Developer(String name, String lastName, String mail) {
this.name = name;
this.lastName = lastName;
this.mail = mail;
}
public String getFirstName() {
return name;
}
public String getLastName() {
return lastName;
}
public String getMail() {
return mail;
}
}
This is the .odt file i am using.
In the Developer class you have getFirstName instead of getName. Hence dev.name won't work.
Here , I want to hardcode some things into db at the action of server starts with Spring commandline runner
Problem :- In this I have checked that if 1L isn't present then do entry for that with Id 1L but still it stores to incremental Id when 1L or 2L or 3L is not present there.
My Entity In which I'm doing entry :-
Product Type
#Data
#Entity
#Table(name = "tbl_product_type_chemical")
public class ProductType implements IBaseData<Long> {
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Id
private Long id;
private String name;
#Column(columnDefinition = "text")
private String description;
}
This is method of Runner :-
private void loadProductTypeNew() throws Exception {
String SUBMODULE = " [Init Data] " + " [loadProductTypeNew()] ";
try {
ProductType fp = productTypeRepository.getOne(1L);
if (null == fp) {
fp = new ProductType();
fp.setId(1L);
fp.setName("FINISH PRODUCT");
productTypeRepository.save(fp);
}
ProductType rm = productTypeRepository.getOne(2L);
if (null != rm) {
rm = new ProductType();
rm.setId(2L);
rm.setName("RAW MATERIAL");
productTypeRepository.save(rm);
}
ProductType sm = productTypeRepository.getOne(3L);
if (null != sm) {
sm = new ProductType();
sm.setId(3L);
sm.setName("SUPPORTING MATERIAL");
productTypeRepository.save(sm);
}
} catch (Exception ex) {
ApplicationLogger.logger.error(SUBMODULE + ex.getMessage(), ex);
throw ex;
}
}
#Override
public void run(String... args) throws Exception {
loadProductTypeNew();`
}
Output :-
9 SUPPORTING MATERIAL
8 RAW MATERIAL
7 FINISH PRODUCT
10 FINISH PRODUCT
11 RAW MATERIAL
12 SUPPORTING MATERIAL
13 RAW MATERIAL
14 SUPPORTING MATERIAL
And I am calling it in run method.If anyone can solve thanks in advance
Nothing in your application should depend on specific values of the id field since it is generated by the database.
I suggest therefore to identify a business key (in your case the name), ensure it is unique with a primary key and use that to determine if a a row needs to be inserted in the database.
Your code would look similar to this
if (productTypeRepository.existsByName(""FINISH PRODUCT")) {
ProductType fp = new ProductType();
fp.setName("FINISH PRODUCT");
productTypeRepository.save(fp);
}
I'm using the Object API with OrientDB, and I need to change one of my fields. I currently have something like:
class Book { String author }
But I want to change it to:
class Book { List<String> authors }
My question is: how do I persist this list of Strings in OrientDB? Do I have to declare the list as #Embedded? Do I have to define the Schema as LINKLIST?
I tried the latter, which resulted in:
Caused by: java.lang.ClassCastException: java.lang.String cannot be cast to com.orientechnologies.orient.core.db.record.OIdentifiable
And, if I make the type in the database an Embbed, then it results in the error:
Caused by: java.lang.IllegalArgumentException: Type EMBEDDED must be a multi value type (collection or map)
Which doesn't provide to much information unfortunately.
So, how can I best fix this?
Start point:
I created a new db from the Java API, and I saved a list of authors.
CLASS BOOK
public class Book {
private List<String> authors;
public void setAuthors (List<String> pAuthors){
this.authors = pAuthors;
}
public List<String> getAuthors(){
return this.authors;
}
}
CLASS MAIN
public class DatabaseTipoObject {
private static String remote="remote:localhost/";
public static void main(String[] args) {
String nomeDb="Object";
String path=remote+nomeDb;
try {
OServerAdmin serverAdmin = new OServerAdmin(path).connect("root", "root");
if(serverAdmin.existsDatabase()){
System.out.println("Database '"+nomeDb +"' exist..");
}
else{
serverAdmin.createDatabase(nomeDb, "object", "plocal");
System.out.println(" Database '"+nomeDb +"' created!..");
}
OObjectDatabaseTx db = new OObjectDatabaseTx (path);
db.open("root","root");
db.getEntityManager().registerEntityClass(Book.class);
Book book = db.newInstance(Book.class);
List<String> myAuthors = new ArrayList();
myAuthors.add("Archimede");
myAuthors.add("Pitagora");
book.setAuthors(myAuthors);
db.save(book);
System.out.println("Data inserted!" );
//get info by query
for (Book book_retrive : db.browseClass(Book.class)) {
System.out.println("#: " +book_retrive.getAuthors().get(0) );
System.out.println("#: " +book_retrive.getAuthors().get(1) );
}
db.close();
serverAdmin.close();
} catch (IOException e) {
e.printStackTrace();
}
}
From Studio:
the object 'Book' was created, and it has the field 'authors' as embeddedlist. (Created automatically)
I am using JDO in GAE. I have two JDO classes having one to many relationship. parent class is
#PersistenceCapable(detachable="true")
#FetchGroup(name="childerns", members={#Persistent(name="aliasName")})
public class IdentityProvider {
#PrimaryKey
#Persistent
private String url;
#Persistent
private String domainName;
#Persistent
#Element(dependent = "true")
private ArrayList<AliasDomain> aliasName = new ArrayList<AliasDomain>();
}
The child classes is
#PersistenceCapable(detachable = "true")
public class AliasDomain {
#Persistent
private String url;
#Persistent
private String aliasName;
#PrimaryKey
#Persistent(valueStrategy = IdGeneratorStrategy.IDENTITY)
private Key key;
}
I am just performing CURD operations on both entity. First i create the parent instance and then i create the child instance as
public void addAliasDomain(AliasDomain domain) {
String url = domain.getUrl();
PersistenceManager pm = PMFSingleton.get().getPersistenceManager();
IdentityProvider idp = null;
Transaction txn = null;
try {
txn = pm.currentTransaction();
txn.begin();
pm.getFetchPlan().addGroup("childerns");
idp = pm.getObjectById(IdentityProvider.class, url);
idp = pm.detachCopy(idp);
idp.getAliasName().add(domain);
pm.makePersistent(idp);
txn.commit();
} catch (Exception e) {
e.printStackTrace();
} finally {
if ( txn.isActive() ) {
txn.rollback();
}
pm.close();
}
}
My issue is created when i delete any child instance. As you see from the above function i link the child to the parents( means add child object into arrayList). So when child is deleted its reference in the parents is not deleted so at the detached time of parents object i got exception which is as
Object of type "user.oauth.jdo.model.IdentityProvider" and identity "yahoo.com" was not detached correctly. Please consult the log for any possible information.
org.datanucleus.exceptions.NucleusUserException: Object of type "user.oauth.jdo.model.IdentityProvider" and identity "yahoo.com" was not detached correctly. Please consult the log for any possible information.
at org.datanucleus.state.JDOStateManager.detachCopy(JDOStateManager.java:2942)
at org.datanucleus.ObjectManagerImpl.detachObjectCopy(ObjectManagerImpl.java:2591)
at org.datanucleus.api.jdo.JDOPersistenceManager.jdoDetachCopy(JDOPersistenceManager.java:1145 )
at org.datanucleus.api.jdo.JDOPersistenceManager.detachCopy(JDOPersistenceManager.java:1174)
at user.oauth.data.broker.IDPJDOBroker.retrieveDomainList(IDPJDOBroker.java:49)
The code of function retreiveDomainList in IDPJDOBroker is
public List retrieveDomainList() {
PersistenceManager pm = PMFSingleton.get().getPersistenceManager();
Query query = pm.newQuery(IdentityProvider.class);
List<IdentityProvider> list = null;
List<IdentityProvider> detachedList = null;
IdentityProvider idp = null;
try {
pm.getFetchPlan().addGroup("childerns");
list = (List<IdentityProvider>) query.execute();
detachedList = new ArrayList<IdentityProvider>();
for(IdentityProvider obj : list){
idp = pm.detachCopy(obj);
OAuthJDOBroker broker = new OAuthJDOBroker();
int actUsers = 0;
if ( idp.getHistory() != null && idp.getHistory().size() > 0) {
actUsers = broker.calculateActiveUser(idp.getUserActiveDuration(),idp.getDomainName());
}
idp.setActiveUsers(actUsers);
detachedList.add(idp);
}
} catch (Exception e) {
e.printStackTrace();
} finally {
query.closeAll();
pm.close();
}
return detachedList;
}
Please tell me what to do? Is it not possible in JDO to delete the child? if it is possible then how to do it properly.
I have just seen this, but in case anyone arrives here, to delete a child object in a one to many relationship you must delete the reference from the parent, the child object will be deleted "transparently"
I have a problem using GAEJ and JDO for storing the data.
This is what I'm working with:
class Usuari.java:
#PrimaryKey
#Persistent(valueStrategy = IdGeneratorStrategy.IDENTITY)
private Key key;
#Persistent
private String email;
#Persistent
private String rol="";
class DBUtils.java:
I've tried with two ways of doing the delete operation:
// This method removes a record from the database using its unique Key
public static boolean eliminar(Key k) throws Exception {
PersistenceManager pm = PMF.get().getPersistenceManager();
String kind;
Long id;
kind = k.getKind();
id = k.getId();
try {
if (k.getKind().equals("Usuari")) {
Usuari u = (Usuari)pm.getObjectById(k);
pm.deletePersistent(u);
_log.log(Level.INFO, "Deleted an entity->kind: " + kind + " id: " + id);
}
return true;
} catch (Exception e) {
_log.log(Level.SEVERE, "Unable to delete an entity->kind: " + kind + " id: " + id);
System.err.println(e.getMessage());
throw e;
}
finally {
pm.close();
}
}
// This method removes a record from the database using its unique Key - too
public static void eliminar2(Key k) throws Exception {
PersistenceManager pm = PMF.get().getPersistenceManager();
javax.jdo.Transaction tx = pm.currentTransaction();
try
{
tx.begin();
if (k.getKind().equals("Usuari")) {
Usuari u = (Usuari) pm.getObjectById(k);
pm.deletePersistent(u);
}
tx.commit();
}
catch (Exception e)
{
if (tx.isActive())
{
tx.rollback();
}
throw e;
}
}
I'm able to create new instances of some class "Usuari" but I can't delete them.
Everytime I call "eliminar" or "eliminar2" methods I get a "No such object" as result of trying to fetch it. I've checked manually and I see the object exists in my admin panel, with its ID and KIND, so I don't know what am I doing wrong.
Any help would be much appreciated.
PM.getObjectById does not take in a Key object, as per the JDO spec. It takes in an identity object, the same type as you would get from pm.getObjectId(obj); suggest you glance through the JDO spec. No doubt if you inspected what is returned from this method you would see that it can't find an object with that 'identity' because a Key is not an identity. You can also do
pm.getObjectById(Usuari.class, key);
which is shown very clearly in GAE documentation.
Still don't get why users are putting #Persistent on every field virtually every type is default persistent; only leads to making code more unreadable.