首页 > 编程技术 > php

PHP操作MSSQL存储过程修改用户密码

发布时间:2016-11-25 16:34

存储过程在数据库的应用中我们用到的非常的多了,下面我们来看一篇关于PHP操作MSSQL存储过程修改用户密码的例子,具体的如下所示。

mssql2008 存储过程 下面可以直接远程修改密码。

 代码如下 复制代码

USE [GameUserDB]
GO
IF EXISTS (SELECT * FROM DBO.SYSOBJECTS WHERE ID = OBJECT_ID(N'[dbo].[UpdateUserInfo]') and OBJECTPROPERTY(ID, N'IsProcedure') = 1)
DROP PROCEDURE [dbo].[UpdateUserInfo]
GO
CREATE PROCEDURE [UpdateUserInfo]
 @dwUserID INT,
 @strCompellation NVARCHAR(16),
 @strQQ NVARCHAR(16),
 @strEmail NVARCHAR(32),
 @strSeatPhone NVARCHAR(32),
 @strMobilePhone NVARCHAR(16),
 @strDwellingPlace NVARCHAR(128),
 @strPostalCode NVARCHAR(8),
 @strUserNote NVARCHAR(256),
 @LogonPass char (32),
 @LogonPass2 char (32),
 @Typ NVARCHAR (50),
 @UserID INT,
 @FaceID INT
WITH ENCRYPTION AS
BEGIN
 IF @TYP='LostPass'
 BEGIN
  IF EXISTS (SELECT UserID FROM AccountsInfo WHERE UserID=@UserID And LogonPass=@LogonPass)
  BEGIN
   UPDATE [AccountsInfo]
   SET  LogonPass  = @LogonPass2 WHERE ( [UserID]  = @UserID)
   SELECT '成功信息:修改登入密码成功!'
  END
  ELSE
  BEGIN
   SELECT '您的原密码输入错误!'
  END
 END 
END
return 0
go

PHP操作存储过程

PHP调用存储过程修改用户密码,本示例直接填写参数,实际环境可以从外部程序提交数据进行处理。

 代码如下 复制代码

<?php
/* 存储过程测试 */
//error_reporting(0);

/* 存储过程: 数据库连接
------------------------------------------------------*/
define('MSDB_HOST', '1.2.3.4');
define('MSDB_PORT', 1433);
define('MSDB_USER', 'yang');
define('MSDB_PASS', 'yangjunwei');
define('MSDB_NAME', 'GameUserDB');
$conn = mssql_connect(MSDB_HOST,MSDB_USER,MSDB_PASS) or die("SQL SERVER 数据库连接失败!");
mssql_select_db(MSDB_NAME);

/* 存储过程: 修改指定用户密码
------------------------------------------------------*/
$action_type = 'LostPass';  // 操作类型
$User_ID = 1;   //用户ID
$User_name = 'yang';  //用户名
$User_pass = md5("123456"); //原用户密码
$User_pass2 = md5("654321"); //新用户密码
$User_null = NULL;

$stmt = mssql_init("UpdateUserInfo", $conn) or die("initialize stored procedure failure");//初始化一个存储过程

mssql_bind($stmt, "@Typ", $action_type, SQLVARCHAR);
mssql_bind($stmt, "@UserID", $User_ID, SQLINT4);
mssql_bind($stmt, "@LogonPass", $User_pass, SQLCHAR);
mssql_bind($stmt, "@LogonPass2", $User_pass2, SQLCHAR);

mssql_bind($stmt, "@dwUserID", $User_null, SQLINT4, false, false);
mssql_bind($stmt, "@strCompellation", $User_null, SQLVARCHAR);
mssql_bind($stmt, "@strQQ", $User_null, SQLVARCHAR);
mssql_bind($stmt, "@strEmail", $User_null, SQLVARCHAR);
mssql_bind($stmt, "@strSeatPhone", $User_null, SQLVARCHAR);
mssql_bind($stmt, "@strMobilePhone", $User_null, SQLVARCHAR);
mssql_bind($stmt, "@strDwellingPlace", $User_null, SQLVARCHAR);
mssql_bind($stmt, "@strPostalCode", $User_null, SQLVARCHAR);
mssql_bind($stmt, "@strUserNote", $User_null, SQLVARCHAR);
mssql_bind($stmt, "@FaceID", $User_null, SQLINT4);

/*
mssql_bind($stmt,"RETVAL",$val,SQLVARCHAR); //用于直接返回return -103此类的值。

$result = mssql_execute($stmt, true); //不能返回结果集,只能得到输出参数
echo $val.'<br />';
echo "This user id is: ".$UserID.'<br />';
echo "This user name is: ".$Accounts.'<br />';
*/

$result = mssql_execute($stmt,false); //返回结果集
$records=mssql_fetch_array($result);
print_r($records);
mssql_next_result($result); //下一个结果集,当等于FALSE的时候下一个就是输出参数

// MSSQL 调试
//die('MSSQL error: ' . mssql_get_last_message());
//exit;

?>

注释:MSSQL数据表大概设计

数据库:QPGameUserDB
数据表:AccountsInfo
数据列:UserID / LogonPass

下面我们来看一篇关于PHP扩展 mssql 连接远程 MSSQL,希望这篇文章能够帮助到各位了解到PHP扩展 mssql 连接远程 MSSQL例子哦。

PHP利用 mssql 扩展连接MSSQL,这里给一个简单的示例,没有做安全考虑,自行处理吧

 代码如下 复制代码

<?php
// 连接数据库
$conn = mssql_connect('hostip:1433','user','pass') or die("SQL SERVER 数据库连接失败!");

// 选择数据库
mssql_select_db('UserInfo', $conn);

// sql语句
$sql = "SELECT TOP 5 * FROM info";
$result = mssql_query($sql);

//打印输出
//print_r($result);

$num = mssql_num_rows($result);
echo '有'.$num."条记录<br>";
if($num){
 //循环出每一条记录
 for( $i=0;$i<$num;$i++ ){
  $Row = mssql_fetch_array($result);
  echo $Row[0].$Row[1]."...<br/>";
 }  
}else{
 echo "暂无数据" ;
}
//关闭连接
mssql_close($conn);
?>

sphinx是一个不错的基于SQL的全文检索引擎插件了,我们今天来看看sphinx 的安装配置及php使用例子吧,具体的如下所示。

先当然是从sphnix网站下载sphinx源码包,当前最新版本是:http://www.sphinxsearch.com/downloads/
当然,还需要保证你的系统已经安装了MySQL。

其次,就是依照官方的安装指导进行安装了,基本步骤如下:

官方入门文档 http://www.sphinxsearch.org/archives/80

1、解压sphinx源码包:

mac 版直接解压就能用

http://sphinxsearch.com/files/sphinx-2.2.10-release-osx10.10-x86_64.tar.gz
centos步骤为:

* [root@localhost src]# wget http://www.sphinxsearch.com/downloads/sphinx-0.9.9.tar.gz
* [root@localhost src]# tar zxvf sphinx-0.9.9.tar.gz
* [root@localhost local]# cd sphinx-0.9.9
* [root@localhost sphinx-0.9.9]# ./configure –prefix=/usr/local/sphinx #注意:这里sphinx已经默认支持了mysql

* [root@localhost sphinx-0.9.9]# make && make install # 其中的“警告”可以忽略
 

2、修改配置文件

* [root@localhost ~]#cd /usr/local/sphinx/etc #进入sphinx的配置文件目录
* [root@localhost etc]# cp sphinx.conf.dist sphinx.conf #新建Sphinx配置文件
* [root@localhost etc]# vim sphinx.conf #编辑sphinx.conf
具体实例配置文件:主要修改mysql 连接信息

source article_src
{
type = mysql #####数据源类型
sql_host = 192.168.1.10 ######mysql主机
sql_user = root ########mysql用户名
sql_pass = pwd############mysql密码
sql_db = test #########mysql数据库名
sql_port= 3306 ###########mysql端口

3、将测试数据导入mysql  test 数据库

mysql -uroot -p test < example.sql
4、建立索引文件

[root@localhost sphinx]# bin/indexer -c etc/sphinx.conf   ### 建立索引文件的命令
5、运行sphinx

bin/searchd
6、运行php测试

php api/test.php -h localhost
查询结果如下

Query '' retrieved 4 of 4 matches in 0.000 sec.
Query stats:

Matches:
1. doc_id=1, weight=1, group_id=1, date_added=2016-05-18 07:06:30
2. doc_id=2, weight=1, group_id=1, date_added=2016-05-18 07:06:30
3. doc_id=3, weight=1, group_id=2, date_added=2016-05-18 07:06:30
4. doc_id=4, weight=1, group_id=2, date_added=2016-05-18 07:06:30


增量索引 实现近实时更新 .


   测试条件:以默认的sphinx.conf配置为例,数据库表的数据也以 example.sql为例。

1.先在mysql中插入一个计数表和两个索引表

CREATE TABLE sph_counter(    counter_id INTEGER PRIMARY KEY NOT NULL,    max_doc_id INTEGER NOT NULL);
2.修改sphinx.conf

source main_src{

       type                = mysql

       sql_host            = localhost

       sql_user            = yourusername

       sql_pass            = yourpassword

       sql_db              = test   //你所用的数据库

       sql_port            = 3306 //所用端口,默认是3306

       sql_query_pre       = SET NAMES utf8

       sql_query_pre       = SET SESSION query_cache_type=OFF       #下面的语句是更新sph_counter表中的 max_doc_id。       sql_query_pre = REPLACE INTO sph_counter SELECT 1, MAX(id) FROM documents

       sql_query = SELECT id, group_id, UNIX_TIMESTAMP(date_added) AS date_added, title,\

                 content FROM documents \

               WHERE id<=( SELECT max_doc_id FROM sph_counter WHERE counter_id=1 )

}

// 注意:delta_src 中的sql_query_pre的个数需和main_src 对应,否则可能搜索不出相应结果

source delta_src: main_src{

         sql_ranged_throttle = 100

         sql_query_pre       = SET NAMES utf8

         sql_query_pre       = SET SESSION query_cache_type=OFF

         sql_query      = SELECT id, group_id, UNIX_TIMESTAMP(date_added) AS date_added, title, content FROM documents\

            WHERE id>( SELECT max_doc_id FROM sph_counter WHERE counter_id=1 )

}

index main //主索引{

       source           = main_src

       path             = /path/to/main

       # example:   /usr/local/sphinx/var/data/main      .............

       charset_type     = utf-8    #这个是支持中文必须要设置的

       chinese_dictionary =/usr/local/sphinx/etc/xdict       #..........其它可以默认

}

//delta可全部复制主索引,然后更改source 和path如下
 

index delta: main //增量索引{

         source = delta_src

         path     = /path/to/delta

         # example:  /usr/local/sphinx/var/data/delta…   

}

其它的配置可都用默认的,如果你设置了分布式检索的索引,那么更改下对应的索引名称即可。

3.重新建立索引:
如果sphinx正在运行,那么首先停止运行,然后,根据sphinx.conf配置文件来建立所有索引,最后,启动服务
 

/usr/local/sphinx/bin/searchd --stop/usr/local/sphinx/bin/indexer -c  /usr/local/sphinx/etc/sphinx.conf --all/usr/local/sphinx/bin/searchd -c  /usr/local/sphinx/etc/sphinx.conf
P.S /usr/local/sphinx/bin/indexer -c  /usr/local/sphinx/etc/sphinx.conf --all --rotate

    这样就不需要停searchd,索引后也不再需要重启searchd了。

如果想测试增量索引是否成功,往数据库表中插入数据,查找是否能够检索到,这个时候检索应该为空,然后,单独重建 delta索引
/usr/local/sphinx/bin/indexer -c /usr/lcoal/sphinx/etc/sphinx.conf delta
查看是否将新的记录进行了索引。如果成功,此时,再用 /usr/local/sphing/bin/search 工具来检索,能够看到,在main索引中检索到的结果为0,而在delta中检索到结果。当然,前提条件是,检索的词,只在后来插入的数据中存在。

接下来的问题是如何让增量索引与主索引合并

4.索引合并
合并两个已有索引 有时比 重新索引所有数据有效,虽然,索引合并时,待合并的两个索引都会被读入内存一次,合并后的内容需写入磁盘一次,即,合并100GB和1GB的两个所以,将导致202GB的IO操作
命令原型:  indexer --merge DSTINDEX  SRCINDEX [--rotate]   将SRCINDEX合并到 DSTINDEX ,所以只有DSTINDEX会改变,如果两个索引都正在提供服务,那么 -- rotate 参数是必须的。例如:将delta合并到main中。
indexer --merge main delta   

5.索引自动更新
需要使用到脚本。
建立两个脚本:build_main_index.sh 和 build_delta_index.sh.

build_main_index.sh:
#!/bin/sh
# 停止正在运行的searchd
/usr/local/sphinx/bin/searchd -c /usr/local/sphinx/etc/mersphinx.conf  --stop >> /usr/local/sphinx/var/log/sphinx/searchd.log
#建立主索引
/usr/local/sphinx/bin/indexer -c  /usr/local/sphinx/etc/mersphinx.conf main >> /usr/local/sphinx/var/log/sphinx/mainindex.log
#启动searchd守护程序
/usr/local/sphinx/bin/searchd >> /usr/local/sphinx/var/log/sphinx/searchd.log

build_delta_index.sh

#!/bin/sh
#停止sphinx服务,将输出重定向
/usr/local/sphinx/bin/searchd –stop >> /usr/local/sphinx/var/log/sphinx/searchd.log
#重新建立索引delta ,将输出重定向
/usr/local/sphinx/bin/indexer delta –c /usr/local/sphinx/etc/sphinx.conf>>/usr/lcoal/sphinx/var/log/sphinx/deltaindex.log
#将delta合并到main中
/usr/local/sphinx/bin/indexer –merge main delta –c /usr/local/sphinx/etc/sphinx.conf >> /usr/lcoal/sphinx/var/log/sphinx/deltaindex.log
#启动服务
/usr/local/sphinx/bin/searchd >> /usr/local/sphinx/var/log/sphinx/searchd.log

脚本写好后,需要编译 chmod +x filename 这样才能运行。即
chmod +x build_main_index.sh
chmod +x build_delta_index.sh

最后,我们需要脚本能够自动运行,以实现,delta索引每5分钟重新建立,和main索引只在午夜2:30时重新建立。

使用crontab 命令 这有俩个地方可作参考 crontab  crontab文件
crontab -e 来编辑 crontab文件,如果之前没有使用,会是一个空的文件。写下下面两条语句
*/30 * * * *  /bin/sh /usr/local/sphinx/etc/build_delta_index.sh > /dev/null 2>&1
30 2 * * * /bin/sh /usr/local/sphinx/etc/build_main_index.sh > /dev/null 2>&1

第一条是表示每30分钟运行 /usr/local/sphinx/etc/下的build_delta_index.sh 脚本,输出重定向。
第二条是表示 每天的 凌晨2:30分运行 /usr/local/sphinx/etc下的build_main_inde.sh 脚本,输出重定向。
关于前面的 5个值的设置,在上面的crontab文件中有详细的描述。关于重定向的解释,请看最上面的Crontab笔记 ,也有crontab的介绍。

保存好后:重新启动服务
 

[root@test1 init.d]# service crond stop
[root@test1 init.d]# service crond start
或者
/etc/init.d/crontab   start

到现在为止,如果脚本写的没有问题,那么build_delta_index.sh将每30分钟运行一次,而build_main_index.sh将在凌晨2:30分才运行。

要验证的话,在脚本中,有将输出重定向到相关的文件,可以查看下文件中的记录是否增多,也可以看下 /usr/local/sphinx/var/log下的 searchd.log 中,每次重建索引都会有记录。

总结
1.索引合并问题,前面已经解释过,两个索引合并时,都要读入,然后还要写一次硬盘,IO操作量很大。而在php API调用时,Query($query,$index)中$index可以设置多个索引名,如Query($query,"main;delta"),也就没有必要一定将两个索引合并,或者,合并的次数不用那么多。
2.还有一个是没有尝试过的,把增量索引存放到共享内存中(/dev/shm)以提高索引性能,减少系统负荷。关于PHP API
如何能够顺利通过PHP页面来进行检索。
首先,在服务器上searchd 必须是运行的。
然后,根据test.php来修改下。
运行,连接时会出现一个很大的问题 errno =13 permission deny. 最后,查到一个英文的网页,是因为SElinux的原因,关于SELinux在网上能搜到。没有很好的解决办法,只能把SELinux设置为不用。使用的命令有下面两个: setenforce 在 /usr/bin 下
setenforce 1 设置SELinux 成为enforcing模式
setenforce 0 设置SELinux 成为permissive模式

如果你在使用PHP连接MySQL报错:SQLSTATE[HY000] [2002] Cant connect to local MySQL server through socket MySQL (2)错误的话可以和小编一起来看如何处理这个连接错误问题。

如下所示,PHP连接MySQL报错:

SQLSTATE[HY000] [2002] Can't connect to local MySQL server through socket 'MySQL' (2)

测试代码如下:

<?php
try
{
 $dsn = 'mysql:dbname=php-note;host=localhost;port=3306;charset=utf8';
 $username = 'root';
 $password = 'root';
 new PDO( $dsn, $username, $password);
}
catch (\PDOException $e)
{
 echo $e->getMessage();
}

【解决方案】

把 host=localhost 改为 host=127.0.0.1 即可!
 
 
连接Mysql提示Can’t connect to local MySQL server through socket的解决方法
 
mysql,Mysqldump,Mysqladmin,php连接mysql服务常会提示下面错误:
ERROR 2002 (HY000): Can't connect to local MySQL server through socket '/var/lib/mysql/mysql.sock' (2)
这是由于修改mysql服务的了socket文件mysql.sock位置,而导致无法通过mysql socket文件连接到mysql服务引起的,具体解决办法如下:

1、查看mysql服务的socket文件位置:

mysql socket文件的位置是在/etc/my.cnf中设置的,cat /etc/my.cnf内容如下:
[mysqld]
datadir=/storage/db/mysql
socket=/storage/db/mysql/mysql.sock
user=mysql
其中socket等于的路径就是socket文件的位置,我们只要修改my.cnf文件,告诉mysql,mysqldump,mysqladmin mysql服务的socket位置在哪里就可以。

2、修改my.cnf文件:

在/etc/my.cnf文件中添加如下内容,并重启mysqls服务,即可解决mysql,mysqldump,mysqladmin的“Can't connect to local MySQL server through socket '/var/lib/mysql/mysql.sock'”问题:
[mysqld]
datadir=/storage/db/mysql
socket=/storage/db/mysql/mysql.sock
[mysql]
socket=/storage/db/mysql/mysql.sock
[mysqldump]
socket=/storage/db/mysql/mysql.sock
[mysqladmin]
socket=/storage/db/mysql/mysql.sock

3、php连接mysql服务提示"Can't connect to local MySQL server through socket..."的解决方法

有时候mysql服务正常运行,用户名密码也完全正确,使用php的mysql_connect函数却连接不了mysql,调用php的mysql_error()函数提示“Can't connect to local MySQL server through socket '/var/lib/mysql/mysql.sock'”,这是我们需要修改/etc/php.ini文件。
在/etc/php.ini文件中"[MySQL]"项下找到"mysql.default_socket",并设置其值指向正确的mysql服务socket文件即可,如:
[MySQL]
...省略n行...
mysql.default_socket = "/storage/db/mysql/mysql.sock"

4、python连接mysql提示"Can't connect to local MySQL server through socket..."的解决方法:

在连接mysql数据库函数中指定socket文件,如下:
#!/usr/bin/python
from MySQLdb import connect
conn = connect(db="pzy", user="root", host="localhost", unix_socket="/storage/db/mysql/mysql.sock")
cur = conn.cursor()
count=cur.execute("show databases")
print 'there has %s dbs' % count
conn.commit()
conn.close()

5、php pdo连接mysql提示"Can't connect to local MySQL server through socket..."的解决方法:


同样在连接字符串添加mysql socket文件的位置即可,如下:
<?php
$dsn = "mysql:host=localhost;dbname=pzy;unix_socket=/storage/db/mysql/mysql.sock";
$db = new PDO($dsn, 'root', '');
$rs = $db->query("SELECT * FROM qrtest");
while($row = $rs->fetch()){
    print_r($row);
}
?>

本文章来为各位介绍一篇关于 Eloquent ORM 概述、模型定义及基本查询详解,希望此文章能够给各位带来帮助哦。

1、引子

在正式进入本节的之前,让我们先来看看什么是ORM。

ORM,即 Object-Relational Mapping(对象关系映射),它的作用是在关系型数据库和业务实体对象之间作一个映射,这样,我们在操作具体的 业务对象时,就不需要再去和复杂的SQL语句打交道,只需简单的操作对象的属性和方法即可。

ORM 两种最常见的实现方式是 ActiveRecord 和 DataMapper,ActiveRecord 尤其流行,在很多框架中都能看到它的身影。两者的区别主要在于 ActiveRecord 中模型与数据表一一对应,而 DataMapper 中模型与数据表是完全分离的。

Laravel 中的 Eloquent ORM 使用的也是 ActiveRecord 实现方式,每一个 Eloquent 模型类对应着数据库中的一张表,我们通过调用模型类的相应方法实现对数据库的增删改查。

2、定义模型

2.1 创建模型

我们使用Artisan命令make:model生成模型类,模型类默认位于app目录下,我们也可以在创建时指定生成目录:

php artisan make:model Models/Post

这样就会在app目录下生成一个Models目录,并且在Models目录下生成一个Post模型类。Laravel 中所有模型类继承自Illuminate\Database\Eloquent\Model类。

2.2 指定表名

如果不手动指定,默认Post对应的数据表为posts,以此类推。也可以通过设置$table属性自定义表名:

public $table = 'posts';

2.3 指定主键

Eloquent默认数据表主键为id,当然也可以通过设置$primaryKey属性来自定义主键:

public $primaryKey = 'id';

2.4 时间戳设置

默认情况下,Eloquent模型类会自动管理时间戳列create_at和update_at(如果定义迁移时设置了这两列的话),如果要取消自动管理,可以设置$timestamps属性为false:

public $timestamps = false;

还有,如果你想要设置时间戳的格式,可以使用$dateFormat属性,该属性决定了日期时间以何种格式存入数据库,以及以何种格式显示:

//设置日期时间格式为Unix时间戳
protected $dateFormat = 'U';

更多关于日期时间格式设置,请参考php官方函数date中format部分。

3、查询数据

3.1 获取多个模型

我们可以使用Eloquent模型上的all方法获取所有模型实例,比如我们通过如下方法获取所有文章:

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;

use App\Http\Requests;
use App\Http\Controllers\Controller;

use App\Models\Post;

class TestController extends Controller
{

    /**
     * Display a listing of the resource.
     *
     * @return Response
     */
    public function index()
    {

        //获取多个Eloquent模型
        $posts = Post::all();
        dd($posts);

    }
}

可见输出结果是模型数组集合,每一个$items元素对应一个Post模型实例。

此外,需要了解的是每一个Eloquent模型本身都是一个查询构建器,所有我们可以调用所有查询构建器上的方法,只不过第一个方法调用都要使用静态方法调用:

$posts = Post::where('id','<',3)->orderBy('id','desc')->take(1)->get();
dd($posts);

 

也许你已经注意到了,模型查询返回结果都是Illuminate\Database\Eloquent\Collection的一个实例,该类实现了ArrayAccess接口,所以我们可以像访问数组一样访问该实例,此外,该Collection类还提供了很多其它有用的方法对查询结果进行处理,详见源码。

既然Eloquent模型是查询构建器,自然也支持分组块获取数据:

Post::chunk(2,function($posts){
    foreach ($posts as $post) {
        echo $post->title.'<br>';
    }
});

输出结果如下:

test 1
test 2
test 3

3.2 获取单个模型

可以使用查询构建器方法获取单个模型实例:

$post = Post::where('id',1)->first();
dd($post);

当然也可以通过Eloquent模型类提供的快捷方法find:

$post = Post::find(1);

 

如果没有找到对应的表记录,会输出null,如果我们想要捕获查询结果为空的异常并进行处理,比如跳转到404页面,可以使用findOrFail或者firstOrFail方法,如果表记录存在,两者返回获取到的第一条记录,否则抛出Illuminate\Database\Eloquent\ModelNotFoundException异常。

3.3 聚合函数查询

如果要对查询结果进行计数、统计、最大值/最小值、平均数等聚合运算,可以使用查询构建器上的对应方法,我们我们查询文章总数:

$count = Post::where('id','>',0)->count();
echo $count;
输出结果为3,又或者我们想要获取文章最大阅读数:

$views = Post::where('id','>',0)->max('views');
echo $views;
输出结果为800。

标签:[!--infotagslink--]

您可能感兴趣的文章: