【问题标题】:how can I make this user (Normal Users) permission to use the procedure如何使该用户(普通用户)有权使用该程序
【发布时间】:2015-02-13 00:11:10
【问题描述】:

//这是我的 MySQL 代码

START TRANSACTION;
BEGIN;
DELIMITER //
CREATE PROCEDURE ViewTempUserInfo (IN Log_Name VARCHAR(45),IN user_Pass VARCHAR(45), 
OUT ID_ INT, out Email VARCHAR(60), out UName VARCHAR(60))

BEGIN

SELECT Costumors_ID into ID_ FROM costumors 
where Costumors_ID= (select Costumors_ID from costumors 
where costumors.Cos_Login_Name = Log_Name and costumors.Cos_Password=user_Pass);

select Cos_Name into UName FROM costumors
where Costumors_ID= ID_;

select Cos_Email into Email FROM costumors 
where Costumors_ID= ID_;

END //
DELIMITER ;
COMMIT;

call ViewTempUserInfo('r','r',@A, @B,@C);

select @A, @B,@C;

GRANT EXECUTE ON PROCEDURE ViewTempUserInfo TO NormalUsers@'%' IDENTIFIED BY '2345NormalUsers2345';
FLUSH PRIVILEGES;

//这是我的Java代码

//STEP 1. Import required packages
import java.sql.*;
import java.util.Properties;

public class Procedure {
   // JDBC driver name and database URL

   static final String DB_URL = "jdbc:mysql://127.0.0.1/testarxampp?allowMultiQueries=true";


    private static String userName= "root";                     //NormalUsers
    private static String password = "DatabasteknikKursen12";   //2345NormalUsers2345
    private static String serverName = "127.0.0.1";
    private static String portNumber = "3306";
    private static String dbName = "testarxampp";

   //  Database credentials
   //static final String USER = "NormalUsers";
   //static final String PASS = "2345NormalUsers2345";

   public static void main(String[] args) {
   Connection conn = null;
   CallableStatement stmt = null;
   try{
      //STEP 2: Register JDBC driver
      Class.forName("com.mysql.jdbc.Driver");

      //STEP 3: Open a connection
      System.out.println("Connecting to database...");
      Properties connectionProps = new Properties();
      connectionProps.put("user", userName);
      connectionProps.put("password", password );
      conn = DriverManager.getConnection("jdbc:mysql://" + serverName + ":" + portNumber + "/" + dbName, connectionProps);

      //STEP 4: Execute a query
        String userNamex = "abli";
        String Passwordx = "ablinana";
      System.out.println("Creating statement...");
      String sql = "{call ViewTempUserInfo(?, ?, ?, ?, ?)}";
      stmt = conn.prepareCall(sql);

      //Bind IN parameter first, then bind OUT parameter

      stmt.setString(1, userNamex); // This would set ID as 102
      // Because second parameter is OUT so register it
      stmt.setString(2, Passwordx);

      stmt.registerOutParameter(3, java.sql.Types.INTEGER);
      stmt.registerOutParameter(4, java.sql.Types.VARCHAR);
      stmt.registerOutParameter(5, java.sql.Types.VARCHAR);

      //Use execute method to run stored procedure.
      System.out.println("Executing stored procedure..." );
      stmt.execute();

      //Retrieve employee name with getXXX method

      System.out.println("Emp Name with ID:" + 
              userNamex + " is " + Passwordx);



      System.out.println("ID    : " + stmt.getInt(3));
      System.out.println("Email    : " + stmt.getString(4));
      System.out.println("name    : " + stmt.getString(5));

      stmt.close();
      conn.close();
   }catch(SQLException se){
      //Handle errors for JDBC
      se.printStackTrace();
   }catch(Exception e){
      //Handle errors for Class.forName
      e.printStackTrace();
   }finally{
      //finally block used to close resources
      try{
         if(stmt!=null)
            stmt.close();
      }catch(SQLException se2){
      }// nothing we can do
      try{
         if(conn!=null)
            conn.close();
      }catch(SQLException se){
         se.printStackTrace();
      }//end finally try
   }//end try
    System.out.println("Goodbye!");

一切正常,我得到以下信息

Connecting to database...
Creating statement...
Executing stored procedure...
Emp Name with ID:abli is ablinana
ID    : 6
Email    : asdf@asdf.se
name    : asdf
Goodbye!

但是如果我改变这些行

private static String userName= "root";                     //NormalUsers
private static String password = "DatabasteknikKursen12";   //2345NormalUsers2345

到这里

private static String userName= "NormalUsers";                      //NormalUsers
private static String password = "2345NormalUsers2345"; //2345NormalUsers2345

我收到以下错误。

Connecting to database...
Creating statement...
java.sql.SQLException: Parameter number 3 is not an OUT parameter
    at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:996)
    at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:935)
    at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:924)
    at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:870)
    at com.mysql.jdbc.CallableStatement.checkIsOutputParam(CallableStatement.java:659)
    at com.mysql.jdbc.CallableStatement.registerOutParameter(CallableStatement.java:1860)
    at Procedure.main(Procedure.java:48)
Goodbye!

了解我在某处做错了什么或如何解决问题而不给予 NormalUsers 所有特权作为 root 用户的人。我使用 mysql-connector-java-1.5.34-bin 并测试切换到 mysql-connector-java-5.1.4 但这没有帮助。在我的许多java类中都有类似的问题。应该足够了:

GRANT EXECUTE ON PROCEDURE ViewTempUserInfo TO NormalUsers@'%' IDENTIFIED BY '2345NormalUsers2345';
FLUSH PRIVILEGES;

??????????????????求求求求解释???????????????

在类似的帖子中,有人给出了我不明白的答案。除了这个

stored procedures executed through jdbc?

TLDR; Change your Callable Statement to reference parameters by index instead of name.

After having a similar problem I updated my JDBC driver mysql-connector-java-5.1.26-bin.jar. The error then changed from

    User does not have access to metadata required to determine stored procedure parameter types. If rights can not be granted, configure connection with "noAccessToProcedureBodies=true" to have driver generate parameters that represent INOUT strings irregardless of actual parameter types.

to

    No access to parameters by name when connection has been configured not to access procedure bodies

I changed my Callable Statement to reference parameters by index instead of name, and hey presto it works.

Updating the driver may not be necessary, just knowing to use indexes instead of names when you don't have metadata access or routine body access.

Good Luck
share|edit

answered Aug 2 '13 at 13:26
Kickaha
603319

知道他的意思的人将 CallableStatement 更改为通过索引而不是名称来引用参数 应该改变什么,谁能解释一下。

【问题讨论】:

  • 您是否尝试以“NormalUsers”身份登录数据库并删除 ViewTempUserInfo 过程?您可以在该用户下部署旧版本的 proc。
  • 不,没有这样做,但我已经以 root 身份登录并创建了 ViewTemplateUserInfo 并多次授予 NormalUser 权限。普通用户可能没有创建、删除程序的权限,只有 EXECUTE。你认为我应该赋予 NormalUser 权限来 DROP、CREAT 程序吗?

标签: java mysql stored-procedures grant


【解决方案1】:

尝试指定数据库名称:

GRANT EXECUTE ON PROCEDURE testarxampp.ViewTempUserInfo TO 'NormalUsers'@'%' IDENTIFIED BY '2345NormalUsers2345';
FLUSH PRIVILEGES;

【讨论】:

  • 我试过了,但现在出现以下错误。 Connecting to database... Creating statement... java.sql.SQLException: User does not have access to metadata required to determine stored procedure parameter types. If rights can not be granted, configure connection with "noAccessToProcedureBodies=true" to have driver generate parameters that represent INOUT strings irregardless of actual parameter types. Goodbye! 无法将整个错误放入此框中
  • 这是 java 连接器的问题。尝试通过命令行或 MySql Workbench 直接连接。
  • 它可以在命令行或 MySQL Workbench 中正常工作。它来自java我有问题。我正在创建一个 Java 应用程序
  • 在 mysql 中添加授权后,它应该存储在 MySql 中,因此当您从 java 连接时,权限应该在那里。尝试从命令行添加它,然后测试从 java 运行您的过程。
  • 我认为驱动程序从数据库中获取过程元数据时出错。当我在调试器中单步执行时,它显示了正确数量的参数,但都具有IN x VARCHAR 的形式。 noAccessToProcedureBodies 是源代码中的一个变量,它告诉驱动程序只信任应用程序。
猜你喜欢
  • 2017-01-25
  • 2013-01-24
  • 2021-08-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多