Search in sources :

Example 1 with Keyspaces

use of org.apache.cassandra.schema.Keyspaces in project cassandra by apache.

the class CreateFunctionStatement method apply.

// TODO: replace affected aggregates !!
public Keyspaces apply(Keyspaces schema) {
    if (ifNotExists && orReplace)
        throw ire("Cannot use both 'OR REPLACE' and 'IF NOT EXISTS' directives");
    UDFunction.assertUdfsEnabled(language);
    if (new HashSet<>(argumentNames).size() != argumentNames.size())
        throw ire("Duplicate argument names for given function %s with argument names %s", functionName, argumentNames);
    rawArgumentTypes.stream().filter(raw -> !raw.isTuple() && raw.isFrozen()).findFirst().ifPresent(t -> {
        throw ire("Argument '%s' cannot be frozen; remove frozen<> modifier from '%s'", t, t);
    });
    if (!rawReturnType.isTuple() && rawReturnType.isFrozen())
        throw ire("Return type '%s' cannot be frozen; remove frozen<> modifier from '%s'", rawReturnType, rawReturnType);
    KeyspaceMetadata keyspace = schema.getNullable(keyspaceName);
    if (null == keyspace)
        throw ire("Keyspace '%s' doesn't exist", keyspaceName);
    List<AbstractType<?>> argumentTypes = rawArgumentTypes.stream().map(t -> t.prepare(keyspaceName, keyspace.types).getType()).collect(toList());
    AbstractType<?> returnType = rawReturnType.prepare(keyspaceName, keyspace.types).getType();
    UDFunction function = UDFunction.create(new FunctionName(keyspaceName, functionName), argumentNames, argumentTypes, returnType, calledOnNullInput, language, body);
    Function existingFunction = keyspace.functions.find(function.name(), argumentTypes).orElse(null);
    if (null != existingFunction) {
        if (existingFunction.isAggregate())
            throw ire("Function '%s' cannot replace an aggregate", functionName);
        if (ifNotExists)
            return schema;
        if (!orReplace)
            throw ire("Function '%s' already exists", functionName);
        if (calledOnNullInput != ((UDFunction) existingFunction).isCalledOnNullInput()) {
            throw ire("Function '%s' must have %s directive", functionName, calledOnNullInput ? "CALLED ON NULL INPUT" : "RETURNS NULL ON NULL INPUT");
        }
        if (!returnType.isCompatibleWith(existingFunction.returnType())) {
            throw ire("Cannot replace function '%s', the new return type %s is not compatible with the return type %s of existing function", functionName, returnType.asCQL3Type(), existingFunction.returnType().asCQL3Type());
        }
    // TODO: update dependent aggregates
    }
    return schema.withAddedOrUpdated(keyspace.withSwapped(keyspace.functions.withAddedOrUpdated(function)));
}
Also used : AuditLogContext(org.apache.cassandra.audit.AuditLogContext) Change(org.apache.cassandra.transport.Event.SchemaChange.Change) CQLStatement(org.apache.cassandra.cql3.CQLStatement) AbstractType(org.apache.cassandra.db.marshal.AbstractType) Schema(org.apache.cassandra.schema.Schema) HashSet(java.util.HashSet) Function(org.apache.cassandra.cql3.functions.Function) Lists(com.google.common.collect.Lists) CQL3Type(org.apache.cassandra.cql3.CQL3Type) FunctionName(org.apache.cassandra.cql3.functions.FunctionName) org.apache.cassandra.auth(org.apache.cassandra.auth) FunctionsDiff(org.apache.cassandra.schema.Functions.FunctionsDiff) UDFunction(org.apache.cassandra.cql3.functions.UDFunction) KeyspacesDiff(org.apache.cassandra.schema.Keyspaces.KeyspacesDiff) ImmutableSet(com.google.common.collect.ImmutableSet) Keyspaces(org.apache.cassandra.schema.Keyspaces) SchemaChange(org.apache.cassandra.transport.Event.SchemaChange) ClientState(org.apache.cassandra.service.ClientState) Set(java.util.Set) AuditLogEntryType(org.apache.cassandra.audit.AuditLogEntryType) List(java.util.List) Collectors.toList(java.util.stream.Collectors.toList) ColumnIdentifier(org.apache.cassandra.cql3.ColumnIdentifier) Target(org.apache.cassandra.transport.Event.SchemaChange.Target) KeyspaceMetadata(org.apache.cassandra.schema.KeyspaceMetadata) FunctionName(org.apache.cassandra.cql3.functions.FunctionName) Function(org.apache.cassandra.cql3.functions.Function) UDFunction(org.apache.cassandra.cql3.functions.UDFunction) AbstractType(org.apache.cassandra.db.marshal.AbstractType) KeyspaceMetadata(org.apache.cassandra.schema.KeyspaceMetadata) UDFunction(org.apache.cassandra.cql3.functions.UDFunction) HashSet(java.util.HashSet)

Example 2 with Keyspaces

use of org.apache.cassandra.schema.Keyspaces in project cassandra by apache.

the class AlterKeyspaceStatement method apply.

public Keyspaces apply(Keyspaces schema) {
    attrs.validate();
    KeyspaceMetadata keyspace = schema.getNullable(keyspaceName);
    if (null == keyspace)
        throw ire("Keyspace '%s' doesn't exist", keyspaceName);
    KeyspaceMetadata newKeyspace = keyspace.withSwapped(attrs.asAlteredKeyspaceParams(keyspace.params));
    if (newKeyspace.params.replication.klass.equals(LocalStrategy.class))
        throw ire("Unable to use given strategy class: LocalStrategy is reserved for internal use.");
    newKeyspace.params.validate(keyspaceName);
    validateNoRangeMovements();
    validateTransientReplication(keyspace.createReplicationStrategy(), newKeyspace.createReplicationStrategy());
    Keyspaces res = schema.withAddedOrUpdated(newKeyspace);
    return res;
}
Also used : Keyspaces(org.apache.cassandra.schema.Keyspaces) KeyspaceMetadata(org.apache.cassandra.schema.KeyspaceMetadata)

Example 3 with Keyspaces

use of org.apache.cassandra.schema.Keyspaces in project cassandra by apache.

the class CreateAggregateStatement method apply.

public Keyspaces apply(Keyspaces schema) {
    if (ifNotExists && orReplace)
        throw ire("Cannot use both 'OR REPLACE' and 'IF NOT EXISTS' directives");
    rawArgumentTypes.stream().filter(raw -> !raw.isTuple() && raw.isFrozen()).findFirst().ifPresent(t -> {
        throw ire("Argument '%s' cannot be frozen; remove frozen<> modifier from '%s'", t, t);
    });
    if (!rawStateType.isTuple() && rawStateType.isFrozen())
        throw ire("State type '%s' cannot be frozen; remove frozen<> modifier from '%s'", rawStateType, rawStateType);
    KeyspaceMetadata keyspace = schema.getNullable(keyspaceName);
    if (null == keyspace)
        throw ire("Keyspace '%s' doesn't exist", keyspaceName);
    /*
         * Resolve the state function
         */
    List<AbstractType<?>> argumentTypes = rawArgumentTypes.stream().map(t -> t.prepare(keyspaceName, keyspace.types).getType()).collect(toList());
    AbstractType<?> stateType = rawStateType.prepare(keyspaceName, keyspace.types).getType();
    List<AbstractType<?>> stateFunctionArguments = Lists.newArrayList(concat(singleton(stateType), argumentTypes));
    Function stateFunction = keyspace.functions.find(stateFunctionName, stateFunctionArguments).orElseThrow(() -> ire("State function %s doesn't exist", stateFunctionString()));
    if (stateFunction.isAggregate())
        throw ire("State function %s isn't a scalar function", stateFunctionString());
    if (!stateFunction.returnType().equals(stateType)) {
        throw ire("State function %s return type must be the same as the first argument type - check STYPE, argument and return types", stateFunctionString());
    }
    /*
         * Resolve the final function and return type
         */
    Function finalFunction = null;
    AbstractType<?> returnType = stateFunction.returnType();
    if (null != finalFunctionName) {
        finalFunction = keyspace.functions.find(finalFunctionName, singletonList(stateType)).orElse(null);
        if (null == finalFunction)
            throw ire("Final function %s doesn't exist", finalFunctionString());
        if (finalFunction.isAggregate())
            throw ire("Final function %s isn't a scalar function", finalFunctionString());
        // override return type with that of the final function
        returnType = finalFunction.returnType();
    }
    /*
         * Validate initial condition
         */
    ByteBuffer initialValue = null;
    if (null != rawInitialValue) {
        initialValue = Terms.asBytes(keyspaceName, rawInitialValue.toString(), stateType);
        if (null != initialValue) {
            try {
                stateType.validate(initialValue);
            } catch (MarshalException e) {
                throw ire("Invalid value for INITCOND of type %s", stateType.asCQL3Type());
            }
        }
        // Converts initcond to a CQL literal and parse it back to avoid another CASSANDRA-11064
        String initialValueString = stateType.asCQL3Type().toCQLLiteral(initialValue, ProtocolVersion.CURRENT);
        assert Objects.equal(initialValue, Terms.asBytes(keyspaceName, initialValueString, stateType));
        if (Constants.NULL_LITERAL != rawInitialValue && UDHelper.isNullOrEmpty(stateType, initialValue))
            throw ire("INITCOND must not be empty for all types except TEXT, ASCII, BLOB");
    }
    if (!((UDFunction) stateFunction).isCalledOnNullInput() && null == initialValue) {
        throw ire("Cannot create aggregate '%s' without INITCOND because state function %s does not accept 'null' arguments", aggregateName, stateFunctionName);
    }
    /*
         * Create or replace
         */
    UDAggregate aggregate = new UDAggregate(new FunctionName(keyspaceName, aggregateName), argumentTypes, returnType, (ScalarFunction) stateFunction, (ScalarFunction) finalFunction, initialValue);
    Function existingAggregate = keyspace.functions.find(aggregate.name(), argumentTypes).orElse(null);
    if (null != existingAggregate) {
        if (!existingAggregate.isAggregate())
            throw ire("Aggregate '%s' cannot replace a function", aggregateName);
        if (ifNotExists)
            return schema;
        if (!orReplace)
            throw ire("Aggregate '%s' already exists", aggregateName);
        if (!returnType.isCompatibleWith(existingAggregate.returnType())) {
            throw ire("Cannot replace aggregate '%s', the new return type %s isn't compatible with the return type %s of existing function", aggregateName, returnType.asCQL3Type(), existingAggregate.returnType().asCQL3Type());
        }
    }
    return schema.withAddedOrUpdated(keyspace.withSwapped(keyspace.functions.withAddedOrUpdated(aggregate)));
}
Also used : AuditLogContext(org.apache.cassandra.audit.AuditLogContext) Change(org.apache.cassandra.transport.Event.SchemaChange.Change) FunctionResource(org.apache.cassandra.auth.FunctionResource) Iterables.transform(com.google.common.collect.Iterables.transform) Permission(org.apache.cassandra.auth.Permission) IResource(org.apache.cassandra.auth.IResource) AbstractType(org.apache.cassandra.db.marshal.AbstractType) ByteBuffer(java.nio.ByteBuffer) org.apache.cassandra.cql3(org.apache.cassandra.cql3) Schema(org.apache.cassandra.schema.Schema) Collections.singletonList(java.util.Collections.singletonList) Lists(com.google.common.collect.Lists) String.join(java.lang.String.join) Collections.singleton(java.util.Collections.singleton) Iterables.concat(com.google.common.collect.Iterables.concat) ProtocolVersion(org.apache.cassandra.transport.ProtocolVersion) org.apache.cassandra.cql3.functions(org.apache.cassandra.cql3.functions) FunctionsDiff(org.apache.cassandra.schema.Functions.FunctionsDiff) Objects(com.google.common.base.Objects) KeyspacesDiff(org.apache.cassandra.schema.Keyspaces.KeyspacesDiff) ImmutableSet(com.google.common.collect.ImmutableSet) Keyspaces(org.apache.cassandra.schema.Keyspaces) SchemaChange(org.apache.cassandra.transport.Event.SchemaChange) ClientState(org.apache.cassandra.service.ClientState) Set(java.util.Set) String.format(java.lang.String.format) AuditLogEntryType(org.apache.cassandra.audit.AuditLogEntryType) List(java.util.List) Collectors.toList(java.util.stream.Collectors.toList) Target(org.apache.cassandra.transport.Event.SchemaChange.Target) KeyspaceMetadata(org.apache.cassandra.schema.KeyspaceMetadata) MarshalException(org.apache.cassandra.serializers.MarshalException) MarshalException(org.apache.cassandra.serializers.MarshalException) AbstractType(org.apache.cassandra.db.marshal.AbstractType) KeyspaceMetadata(org.apache.cassandra.schema.KeyspaceMetadata) ByteBuffer(java.nio.ByteBuffer)

Example 4 with Keyspaces

use of org.apache.cassandra.schema.Keyspaces in project cassandra by apache.

the class CreateTypeStatement method apply.

public Keyspaces apply(Keyspaces schema) {
    KeyspaceMetadata keyspace = schema.getNullable(keyspaceName);
    if (null == keyspace)
        throw ire("Keyspace '%s' doesn't exist", keyspaceName);
    UserType existingType = keyspace.types.getNullable(bytes(typeName));
    if (null != existingType) {
        if (ifNotExists)
            return schema;
        throw ire("A user type with name '%s' already exists", typeName);
    }
    Set<FieldIdentifier> usedNames = new HashSet<>();
    for (FieldIdentifier name : fieldNames) if (!usedNames.add(name))
        throw ire("Duplicate field name '%s' in type '%s'", name, typeName);
    for (CQL3Type.Raw type : rawFieldTypes) {
        if (type.isCounter())
            throw ire("A user type cannot contain counters");
        if (type.isUDT() && !type.isFrozen())
            throw ire("A user type cannot contain non-frozen UDTs");
    }
    List<AbstractType<?>> fieldTypes = rawFieldTypes.stream().map(t -> t.prepare(keyspaceName, keyspace.types).getType()).collect(toList());
    UserType udt = new UserType(keyspaceName, bytes(typeName), fieldNames, fieldTypes, true);
    return schema.withAddedOrUpdated(keyspace.withSwapped(keyspace.types.with(udt)));
}
Also used : AuditLogContext(org.apache.cassandra.audit.AuditLogContext) Change(org.apache.cassandra.transport.Event.SchemaChange.Change) java.util(java.util) Keyspaces(org.apache.cassandra.schema.Keyspaces) SchemaChange(org.apache.cassandra.transport.Event.SchemaChange) Permission(org.apache.cassandra.auth.Permission) ClientState(org.apache.cassandra.service.ClientState) CQLStatement(org.apache.cassandra.cql3.CQLStatement) FieldIdentifier(org.apache.cassandra.cql3.FieldIdentifier) ByteBufferUtil.bytes(org.apache.cassandra.utils.ByteBufferUtil.bytes) AbstractType(org.apache.cassandra.db.marshal.AbstractType) AuditLogEntryType(org.apache.cassandra.audit.AuditLogEntryType) Collectors.toList(java.util.stream.Collectors.toList) CQL3Type(org.apache.cassandra.cql3.CQL3Type) Target(org.apache.cassandra.transport.Event.SchemaChange.Target) Types(org.apache.cassandra.schema.Types) UTName(org.apache.cassandra.cql3.UTName) KeyspaceMetadata(org.apache.cassandra.schema.KeyspaceMetadata) KeyspacesDiff(org.apache.cassandra.schema.Keyspaces.KeyspacesDiff) UserType(org.apache.cassandra.db.marshal.UserType) CQL3Type(org.apache.cassandra.cql3.CQL3Type) AbstractType(org.apache.cassandra.db.marshal.AbstractType) FieldIdentifier(org.apache.cassandra.cql3.FieldIdentifier) KeyspaceMetadata(org.apache.cassandra.schema.KeyspaceMetadata) UserType(org.apache.cassandra.db.marshal.UserType)

Aggregations

KeyspaceMetadata (org.apache.cassandra.schema.KeyspaceMetadata)4 Keyspaces (org.apache.cassandra.schema.Keyspaces)4 Collectors.toList (java.util.stream.Collectors.toList)3 AuditLogContext (org.apache.cassandra.audit.AuditLogContext)3 AuditLogEntryType (org.apache.cassandra.audit.AuditLogEntryType)3 AbstractType (org.apache.cassandra.db.marshal.AbstractType)3 KeyspacesDiff (org.apache.cassandra.schema.Keyspaces.KeyspacesDiff)3 ClientState (org.apache.cassandra.service.ClientState)3 SchemaChange (org.apache.cassandra.transport.Event.SchemaChange)3 Change (org.apache.cassandra.transport.Event.SchemaChange.Change)3 Target (org.apache.cassandra.transport.Event.SchemaChange.Target)3 ImmutableSet (com.google.common.collect.ImmutableSet)2 Lists (com.google.common.collect.Lists)2 List (java.util.List)2 Set (java.util.Set)2 Permission (org.apache.cassandra.auth.Permission)2 CQL3Type (org.apache.cassandra.cql3.CQL3Type)2 CQLStatement (org.apache.cassandra.cql3.CQLStatement)2 FunctionsDiff (org.apache.cassandra.schema.Functions.FunctionsDiff)2 Schema (org.apache.cassandra.schema.Schema)2