IntegralTypeEffectiveStatementImpl( final StmtContext<String, TypeStatement, EffectiveStatement<String, TypeStatement>> ctx, final RangeRestrictedTypeBuilder<T, N> builder) { super(ctx); for (EffectiveStatement<?, ?> stmt : effectiveSubstatements()) { if (stmt instanceof RangeEffectiveStatementImpl) { final RangeEffectiveStatementImpl rangeStmt = (RangeEffectiveStatementImpl)stmt; builder.setRangeConstraint(rangeStmt, rangeStmt.argument()); } if (stmt instanceof UnknownSchemaNode) { builder.addUnknownSchemaNode((UnknownSchemaNode)stmt); } } try { typeDefinition = builder.build(); } catch (InvalidRangeConstraintException e) { throw new SourceException(ctx.getStatementSourceReference(), e, "Invalid range constraint: %s", e.getOffendingRanges()); } }
private static <C extends Number & Comparable<C>> List<ValueRange> ensureResolvedRanges( final List<ValueRange> unresolved, final Range<C> baseRange) { // First check if we need to resolve anything at all for (ValueRange c : unresolved) { if (c.lowerBound() instanceof UnresolvedNumber || c.upperBound() instanceof UnresolvedNumber) { return resolveRanges(unresolved, baseRange); } } // No need, just return the same list return unresolved; }
@SuppressWarnings("checkstyle:hiddenField") public final void setRangeConstraint(final @NonNull ConstraintMetaDefinition constraint, final @NonNull List<ValueRange> ranges) { checkState(this.ranges == null, "Range constraint already defined as %s %s", this.ranges, this.constraint); this.constraint = requireNonNull(constraint); this.ranges = ImmutableList.copyOf(ranges); touch(); }
final RangeConstraint<N> calculateRangeConstraint(final RangeConstraint<N> baseRangeConstraint) { if (ranges == null) { return baseRangeConstraint; } // Run through alternatives and resolve them against the base type final RangeSet<N> baseRangeSet = baseRangeConstraint.getAllowedRanges(); Verify.verify(!baseRangeSet.isEmpty(), "Base type %s does not define constraints", getBaseType()); final Range<N> baseRange = baseRangeSet.span(); final List<ValueRange> resolvedRanges = ensureResolvedRanges(ranges, baseRange); // Next up, ensure the of boundaries match base constraints final RangeSet<N> typedRanges = ensureTypedRanges(resolvedRanges, baseRange.lowerEndpoint().getClass()); // Now verify if new ranges are strict subset of base ranges if (!baseRangeSet.enclosesAll(typedRanges)) { throw new InvalidRangeConstraintException(typedRanges, "Range constraint %s is not a subset of parent constraint %s", typedRanges, baseRangeSet); } return new ResolvedRangeConstraint<>(constraint, typedRanges); }
@SuppressWarnings("unchecked") private static <T extends Number & Comparable<T>> RangeSet<T> ensureTypedRanges(final List<ValueRange> ranges, final Class<? extends Number> clazz) { final Builder<T> builder = ImmutableRangeSet.builder(); for (ValueRange range : ranges) { if (!clazz.isInstance(range.lowerBound()) || !clazz.isInstance(range.upperBound())) { return typedRanges(ranges, clazz); } builder.add(Range.closed((T) range.lowerBound(), (T)range.upperBound())); } return builder.build(); }
final RangeConstraint<N> calculateRangeConstraint(final RangeConstraint<N> baseRangeConstraint) { if (ranges == null) { return baseRangeConstraint; } // Run through alternatives and resolve them against the base type final RangeSet<N> baseRangeSet = baseRangeConstraint.getAllowedRanges(); Verify.verify(!baseRangeSet.isEmpty(), "Base type %s does not define constraints", getBaseType()); final Range<N> baseRange = baseRangeSet.span(); final List<ValueRange> resolvedRanges = ensureResolvedRanges(ranges, baseRange); // Next up, ensure the of boundaries match base constraints final RangeSet<N> typedRanges = ensureTypedRanges(resolvedRanges, baseRange.lowerEndpoint().getClass()); // Now verify if new ranges are strict subset of base ranges if (!baseRangeSet.enclosesAll(typedRanges)) { throw new InvalidRangeConstraintException(typedRanges, "Range constraint %s is not a subset of parent constraint %s", typedRanges, baseRangeSet); } return new ResolvedRangeConstraint<>(constraint, typedRanges); }
@SuppressWarnings("unchecked") private static <T extends Number & Comparable<T>> RangeSet<T> ensureTypedRanges(final List<ValueRange> ranges, final Class<? extends Number> clazz) { final Builder<T> builder = ImmutableRangeSet.builder(); for (ValueRange range : ranges) { if (!clazz.isInstance(range.lowerBound()) || !clazz.isInstance(range.upperBound())) { return typedRanges(ranges, clazz); } builder.add(Range.closed((T) range.lowerBound(), (T)range.upperBound())); } return builder.build(); }
DecimalTypeEffectiveStatementImpl( final StmtContext<String, TypeStatement, EffectiveStatement<String, TypeStatement>> ctx, final DecimalTypeDefinition baseType) { super(ctx); final RangeRestrictedTypeBuilder<DecimalTypeDefinition, BigDecimal> builder = RestrictedTypes.newDecima64Builder(baseType, AbstractTypeStatementSupport.typeEffectiveSchemaPath(ctx)); for (EffectiveStatement<?, ?> stmt : effectiveSubstatements()) { if (stmt instanceof RangeEffectiveStatementImpl) { final RangeEffectiveStatementImpl range = (RangeEffectiveStatementImpl) stmt; builder.setRangeConstraint(range, range.argument()); } if (stmt instanceof FractionDigitsEffectiveStatement) { final Integer digits = ((FractionDigitsEffectiveStatement)stmt).argument(); SourceException.throwIf(baseType.getFractionDigits() != digits, ctx.getStatementSourceReference(), "Cannot override fraction-digits from base type %s to %s", baseType, digits); } if (stmt instanceof UnknownSchemaNode) { builder.addUnknownSchemaNode((UnknownSchemaNode)stmt); } } typeDefinition = builder.build(); }
@SuppressWarnings("checkstyle:hiddenField") public final void setRangeConstraint(final @NonNull ConstraintMetaDefinition constraint, final @NonNull List<ValueRange> ranges) { checkState(this.ranges == null, "Range constraint already defined as %s %s", this.ranges, this.constraint); this.constraint = requireNonNull(constraint); this.ranges = ImmutableList.copyOf(ranges); touch(); }
private static <C extends Number & Comparable<C>> List<ValueRange> ensureResolvedRanges( final List<ValueRange> unresolved, final Range<C> baseRange) { // First check if we need to resolve anything at all for (ValueRange c : unresolved) { if (c.lowerBound() instanceof UnresolvedNumber || c.upperBound() instanceof UnresolvedNumber) { return resolveRanges(unresolved, baseRange); } } // No need, just return the same list return unresolved; }