@Override public URI getEntityURI(ProjectEntity entity) { return URI.create( format( "urn:test:entity:%s:%d", entity.getProjectEntityType().name(), entity.id() ) ); }
private <C extends UserPasswordConfiguration<C>, T extends ConfigurationProperty<C>> void cleanupType(PropertyType<T> propertyType, String configurationName) { //noinspection unchecked propertyService // Looks for all entities which have a property pointing to this configuration .searchWithPropertyValue( (Class<? extends PropertyType<T>>) propertyType.getClass(), (entityType, id) -> entityType.getEntityFn(structureService).apply(id), property -> StringUtils.equals(property.getConfiguration().getName(), configurationName) ) // Deleting this property .forEach(projectEntity -> propertyService.deleteProperty(projectEntity, propertyType.getTypeName())); } }
private Event toEvent(ResultSet rs, BiFunction<ProjectEntityType, ID, ProjectEntity> entityLoader, Function<String, EventType> eventTypeLoader) throws SQLException { // Event type name String eventTypeName = rs.getString("event_type"); // Signature Signature signature = readSignature(rs, "event_time", "event_user"); // Entities Map<ProjectEntityType, ProjectEntity> entities = new LinkedHashMap<>(); for (ProjectEntityType type : ProjectEntityType.values()) { int entityId = rs.getInt(type.name()); if (!rs.wasNull()) { ProjectEntity entity = entityLoader.apply(type, ID.of(entityId)); entities.put(type, entity); } } // Reference (if any) ProjectEntityType refEntity = getEnum(ProjectEntityType.class, rs, "ref"); // Values Map<String, NameValue> values = loadValues(rs); // OK return new Event( eventTypeLoader.apply(eventTypeName), signature, entities, refEntity, values ); }
@Override public <T> Event propertyChange(ProjectEntity entity, PropertyType<T> propertyType) { return Event.of(PROPERTY_CHANGE) .withRef(entity) .with("entity", entity.getProjectEntityType().getDisplayName()) .with("property", new NameValue( propertyType.getTypeName(), propertyType.getName() )) .get(); }
private String expandExpression(String expression, EventRenderer eventRenderer) { if (StringUtils.startsWith(expression, ":")) { String valueKey = expression.substring(1); NameValue value = values.get(valueKey); if (value == null) { throw new EventMissingValueException(eventType.getTemplate(), valueKey); } return eventRenderer.render(valueKey, value, this); } else if ("REF".equals(expression)) { if (ref == null) { throw new EventMissingRefEntityException(eventType.getTemplate()); } else { ProjectEntity entity = entities.get(ref); if (entity == null) { throw new EventMissingEntityException(eventType.getTemplate(), ref); } return eventRenderer.render(entity, this); } } else { // Project entity type ProjectEntityType projectEntityType = ProjectEntityType.valueOf(expression); // Gets the corresponding entity ProjectEntity projectEntity = entities.get(projectEntityType); if (projectEntity == null) { throw new EventMissingEntityException(eventType.getTemplate(), projectEntityType); } // Rendering return eventRenderer.render(projectEntity, this); } }
@Override public <T> Event propertyDelete(ProjectEntity entity, PropertyType<T> propertyType) { return Event.of(PROPERTY_DELETE) .withRef(entity) .with("entity", entity.getProjectEntityType().getDisplayName()) .with("property", new NameValue( propertyType.getTypeName(), propertyType.getName() )) .get(); }
@Override @Cacheable(cacheNames = "properties", key = "#typeName + #entityType.name() + #entityId.value") public TProperty loadProperty(String typeName, ProjectEntityType entityType, ID entityId) { return getFirstItem( String.format( "SELECT * FROM PROPERTIES WHERE TYPE = :type AND %s = :entityId", entityType.name() ), params("type", typeName).addValue("entityId", entityId.getValue()), (rs, rowNum) -> toProperty(rs) ); }
@Override public URI getEntityPage(ProjectEntity entity) { return page("entity:%s:%d", entity.getProjectEntityType().name(), entity.id()); }
@Override public <T extends ProjectEntity> List<LinkDefinition<T>> getLinkDefinitions(ProjectEntityType projectEntityType) { List<LinkDefinition<T>> definitions = new ArrayList<>(); contributors.forEach(contributor -> { if (contributor.applyTo(projectEntityType)) { try { @SuppressWarnings("unchecked") ResourceDecorationContributor<T> tResourceDecorationContributor = (ResourceDecorationContributor<T>) contributor; definitions.addAll(tResourceDecorationContributor.getLinkDefinitions()); } catch (Exception ex) { // Logging logService.log( ApplicationLogEntry.fatal( ex, NameDescription.nd( "ui-resource-decoration", "Issue when collecting UI resource decoration" ), contributor.getClass().getName() ) .withDetail("ui-resource-type", projectEntityType.name()) .withDetail("ui-resource-decorator", contributor.getClass().getName()) ); } } }); return definitions; } }
@Override public Optional<Event> getLastEvent(ProjectEntityType entityType, ID entityId, EventType eventType, BiFunction<ProjectEntityType, ID, ProjectEntity> entityLoader, Function<String, EventType> eventTypeLoader) { return getOptional( format("SELECT * FROM EVENTS WHERE %s = :entityId AND EVENT_TYPE = :eventType ORDER BY ID DESC LIMIT 1", entityType.name()), params("entityId", entityId.get()).addValue("eventType", eventType.getId()), (ResultSet rs, int num) -> toEvent(rs, entityLoader, eventTypeLoader) ); }
@Override public Optional<Signature> getLastEventSignature(ProjectEntityType entityType, ID entityId, EventType eventType) { return getOptional( format("SELECT * FROM EVENTS WHERE %s = :entityId AND EVENT_TYPE = :eventType ORDER BY ID DESC LIMIT 1", entityType.name()), params("entityId", entityId.get()).addValue("eventType", eventType.getId()), (ResultSet rs, int num) -> readSignature(rs, "event_time", "event_user") ); }
@Override public Optional<EntityDataStoreRecord> getById(ProjectEntity entity, int id) { return getOptional( String.format( "SELECT * FROM ENTITY_DATA_STORE " + "WHERE %s = :entityId " + "AND ID = :id", entity.getProjectEntityType().name() ), params("id", id).addValue("entityId", entity.id()), (rs, rowNum) -> toEntityDataStoreRecord(entity, rs) ); }
@Override public int getCountByCategory(ProjectEntity entity, String category) { return getNamedParameterJdbcTemplate().queryForObject( String.format( "SELECT COUNT(*) FROM ENTITY_DATA_STORE " + "WHERE %s = :entityId " + "AND CATEGORY = :category ", entity.getProjectEntityType().name() ), params("entityId", entity.id()) .addValue("category", category), Integer.class ); }
@Override public void post(Event event) { StringBuilder sql = new StringBuilder("INSERT INTO EVENTS(EVENT_VALUES, EVENT_TIME, EVENT_USER, EVENT_TYPE, REF"); MapSqlParameterSource params = new MapSqlParameterSource(); params.addValue("eventValues", writeJson(event.getValues())); params.addValue("eventTime", dateTimeForDB(event.getSignature().getTime())); params.addValue("eventUser", event.getSignature().getUser().getName()); params.addValue("eventType", event.getEventType().getId()); params.addValue("ref", event.getRef() != null ? event.getRef().name() : null); for (ProjectEntityType type : event.getEntities().keySet()) { sql.append(", ").append(type.name()); } sql.append(") VALUES (:eventValues, :eventTime, :eventUser, :eventType, :ref"); for (Map.Entry<ProjectEntityType, ProjectEntity> entry : event.getEntities().entrySet()) { ProjectEntityType type = entry.getKey(); ProjectEntity entity = entry.getValue(); String typeEntry = type.name().toLowerCase(); sql.append(", :").append(typeEntry); params.addValue(typeEntry, entity.id()); } sql.append(")"); getNamedParameterJdbcTemplate().update( sql.toString(), params ); }
@Override @CacheEvict(cacheNames = "properties", key = "#typeName + #entityType.name() + #entityId.value") public Ack deleteProperty(String typeName, ProjectEntityType entityType, ID entityId) { return Ack.one( getNamedParameterJdbcTemplate().update( String.format( "DELETE FROM PROPERTIES WHERE TYPE = :type AND %s = :entityId", entityType.name() ), params("type", typeName).addValue("entityId", entityId.getValue()) ) ); }
@Override public int getCountByCategoryAndName(ProjectEntity entity, String category, String name) { return getNamedParameterJdbcTemplate().queryForObject( String.format( "SELECT COUNT(*) FROM ENTITY_DATA_STORE " + "WHERE %s = :entityId " + "AND CATEGORY = :category " + "AND NAME = :name ", entity.getProjectEntityType().name() ), params("entityId", entity.id()) .addValue("category", category) .addValue("name", name), Integer.class ); }
@Override public List<Event> query(ProjectEntityType entityType, ID entityId, int offset, int count, BiFunction<ProjectEntityType, ID, ProjectEntity> entityLoader, Function<String, EventType> eventTypeLoader) { return getNamedParameterJdbcTemplate().query( format("SELECT * FROM EVENTS WHERE %s = :entityId", entityType.name()) + " ORDER BY ID DESC" + " LIMIT :count OFFSET :offset", params("entityId", entityId.get()) .addValue("count", count) .addValue("offset", offset), (rs, num) -> toEvent(rs, entityLoader, eventTypeLoader) ); }
@Override public void deleteByName(ProjectEntity entity, String category, String name) { getNamedParameterJdbcTemplate().update( String.format( "DELETE FROM ENTITY_DATA_STORE " + "WHERE %s = :entityId " + "AND CATEGORY = :category " + "AND NAME = :name", entity.getProjectEntityType().name() ), params("entityId", entity.id()) .addValue("category", category) .addValue("name", name) ); }
@Override public void deleteByGroup(ProjectEntity entity, String category, String groupName) { getNamedParameterJdbcTemplate().update( String.format( "DELETE FROM ENTITY_DATA_STORE " + "WHERE %s = :entityId " + "AND CATEGORY = :category " + "AND GROUPID = :groupId", entity.getProjectEntityType().name() ), params("entityId", entity.id()) .addValue("category", category) .addValue("groupId", groupName) ); }