Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance. Project price only 1 $
You can buy this project and download/modify it how often you want.
/*
* Copyright 2004-2019 H2 Group. Multiple-Licensed under the MPL 2.0,
* and the EPL 1.0 (https://h2database.com/html/license.html).
* Initial Developer: H2 Group
*/
package org.h2.engine;
import java.util.ArrayList;
import java.util.Arrays;
import org.h2.api.ErrorCode;
import org.h2.message.DbException;
import org.h2.message.Trace;
import org.h2.schema.Schema;
import org.h2.security.SHA256;
import org.h2.table.DualTable;
import org.h2.table.MetaTable;
import org.h2.table.RangeTable;
import org.h2.table.Table;
import org.h2.table.TableType;
import org.h2.table.TableView;
import org.h2.util.MathUtils;
import org.h2.util.StringUtils;
import org.h2.util.Utils;
/**
* Represents a user object.
*/
public class User extends RightOwner {
private final boolean systemUser;
private byte[] salt;
private byte[] passwordHash;
private boolean admin;
public User(Database database, int id, String userName, boolean systemUser) {
super(database, id, userName, Trace.USER);
this.systemUser = systemUser;
}
public void setAdmin(boolean admin) {
this.admin = admin;
}
public boolean isAdmin() {
return admin;
}
/**
* Set the salt and hash of the password for this user.
*
* @param salt the salt
* @param hash the password hash
*/
public void setSaltAndHash(byte[] salt, byte[] hash) {
this.salt = salt;
this.passwordHash = hash;
}
/**
* Set the user name password hash. A random salt is generated as well.
* The parameter is filled with zeros after use.
*
* @param userPasswordHash the user name password hash
*/
public void setUserPasswordHash(byte[] userPasswordHash) {
if (userPasswordHash != null) {
if (userPasswordHash.length == 0) {
salt = passwordHash = userPasswordHash;
} else {
salt = new byte[Constants.SALT_LEN];
MathUtils.randomBytes(salt);
passwordHash = SHA256.getHashWithSalt(userPasswordHash, salt);
}
}
}
@Override
public String getCreateSQLForCopy(Table table, String quotedName) {
throw DbException.throwInternalError(toString());
}
@Override
public String getCreateSQL() {
return getCreateSQL(true);
}
@Override
public String getDropSQL() {
return null;
}
/**
* Checks that this user has the given rights for this database object.
*
* @param table the database object
* @param rightMask the rights required
* @throws DbException if this user does not have the required rights
*/
public void checkRight(Table table, int rightMask) {
if (!hasRight(table, rightMask)) {
throw DbException.get(ErrorCode.NOT_ENOUGH_RIGHTS_FOR_1, table.getSQL(false));
}
}
/**
* See if this user has the given rights for this database object.
*
* @param table the database object, or null for schema-only check
* @param rightMask the rights required
* @return true if the user has the rights
*/
public boolean hasRight(Table table, int rightMask) {
if (rightMask != Right.SELECT && !systemUser && table != null) {
table.checkWritingAllowed();
}
if (admin) {
return true;
}
Role publicRole = database.getPublicRole();
if (publicRole.isRightGrantedRecursive(table, rightMask)) {
return true;
}
if (table instanceof MetaTable || table instanceof DualTable || table instanceof RangeTable) {
// everybody has access to the metadata information
return true;
}
if (table != null) {
if (hasRight(null, Right.ALTER_ANY_SCHEMA)) {
return true;
}
TableType tableType = table.getTableType();
if (TableType.VIEW == tableType) {
TableView v = (TableView) table;
if (v.getOwner() == this) {
// the owner of a view has access:
// SELECT * FROM (SELECT * FROM ...)
return true;
}
} else if (tableType == null) {
// function table
return true;
}
if (table.isTemporary() && !table.isGlobalTemporary()) {
// the owner has all rights on local temporary tables
return true;
}
}
return isRightGrantedRecursive(table, rightMask);
}
/**
* Get the CREATE SQL statement for this object.
*
* @param password true if the password (actually the salt and hash) should
* be returned
* @return the SQL statement
*/
public String getCreateSQL(boolean password) {
StringBuilder buff = new StringBuilder("CREATE USER IF NOT EXISTS ");
getSQL(buff, true);
if (comment != null) {
buff.append(" COMMENT ");
StringUtils.quoteStringSQL(buff, comment);
}
if (password) {
buff.append(" SALT '");
StringUtils.convertBytesToHex(buff, salt).
append("' HASH '");
StringUtils.convertBytesToHex(buff, passwordHash).
append('\'');
} else {
buff.append(" PASSWORD ''");
}
if (admin) {
buff.append(" ADMIN");
}
return buff.toString();
}
/**
* Check the password of this user.
*
* @param userPasswordHash the password data (the user password hash)
* @return true if the user password hash is correct
*/
boolean validateUserPasswordHash(byte[] userPasswordHash) {
if (userPasswordHash.length == 0 && passwordHash.length == 0) {
return true;
}
if (userPasswordHash.length == 0) {
userPasswordHash = SHA256.getKeyPasswordHash(getName(), new char[0]);
}
byte[] hash = SHA256.getHashWithSalt(userPasswordHash, salt);
return Utils.compareSecure(hash, passwordHash);
}
/**
* Check if this user has admin rights. An exception is thrown if he does
* not have them.
*
* @throws DbException if this user is not an admin
*/
public void checkAdmin() {
if (!admin) {
throw DbException.get(ErrorCode.ADMIN_RIGHTS_REQUIRED);
}
}
/**
* Check if this user has schema admin rights. An exception is thrown if he
* does not have them.
*
* @throws DbException if this user is not a schema admin
*/
public void checkSchemaAdmin() {
if (!hasRight(null, Right.ALTER_ANY_SCHEMA)) {
throw DbException.get(ErrorCode.ADMIN_RIGHTS_REQUIRED);
}
}
@Override
public int getType() {
return DbObject.USER;
}
@Override
public ArrayList getChildren() {
ArrayList children = new ArrayList<>();
for (Right right : database.getAllRights()) {
if (right.getGrantee() == this) {
children.add(right);
}
}
for (Schema schema : database.getAllSchemas()) {
if (schema.getOwner() == this) {
children.add(schema);
}
}
return children;
}
@Override
public void removeChildrenAndResources(Session session) {
for (Right right : database.getAllRights()) {
if (right.getGrantee() == this) {
database.removeDatabaseObject(session, right);
}
}
database.removeMeta(session, getId());
salt = null;
Arrays.fill(passwordHash, (byte) 0);
passwordHash = null;
invalidate();
}
@Override
public void checkRename() {
// ok
}
/**
* Check that this user does not own any schema. An exception is thrown if
* he owns one or more schemas.
*
* @throws DbException if this user owns a schema
*/
public void checkOwnsNoSchemas() {
for (Schema s : database.getAllSchemas()) {
if (this == s.getOwner()) {
throw DbException.get(ErrorCode.CANNOT_DROP_2, getName(), s.getName());
}
}
}
}