為了方便大家查找,整理內容如下:
1. MySQL(http://www.mysql.com)mm.mysql-2.0.2-bin.jar
Class.forName( "org.gjt.mm.mysql.Driver" );
cn = DriverManager.getConnection( "jdbc:mysql://MyDbComputerNameOrIP:3306/myDatabaseName", sUsr, sPwd );
2. PostgreSQL(http://www.de.postgresql.org)pgjdbc2.jar
Class.forName( "org.postgresql.Driver" );
cn = DriverManager.getConnection( "jdbc:postgresql://MyDbComputerNameOrIP/myDatabaseName", sUsr, sPwd );
3. Oracle(http://www.oracle.com/ip/deploy/database/oracle9i/)classes12.zip
Class.forName( "oracle.jdbc.driver.OracleDriver" );
cn = DriverManager.getConnection( "jdbc:oracle:thin:@MyDbComputerNameOrIP:1521:ORCL", sUsr, sPwd );
4. Sybase(http://jtds.sourceforge.net)jconn2.jar
Class.forName( "com.sybase.jdbc2.jdbc.SybDriver" );
cn = DriverManager.getConnection( "jdbc:sybase:Tds:MyDbComputerNameOrIP:2638", sUsr, sPwd );
//(Default-Username/Password: "dba"/"sql")
5. Microsoft SQLServer(http://jtds.sourceforge.net)
Class.forName( "net.sourceforge.jtds.jdbc.Driver" );
cn = DriverManager.getConnection( "jdbc:jtds:sqlserver://MyDbComputerNameOrIP:1433/master", sUsr, sPwd );
6. Microsoft SQLServer(http://www.microsoft.com)
Class.forName( "com.microsoft.jdbc.sqlserver.SQLServerDriver" );
cn = DriverManager.getConnection( "jdbc:microsoft:sqlserver://MyDbComputerNameOrIP:1433;databaseName=master", sUsr, sPwd );
7. ODBC
Class.forName( "sun.jdbc.odbc.JdbcOdbcDriver" );
Connection cn = DriverManager.getConnection( "jdbc:odbc:" + sDsn, sUsr, sPwd );
8.DB2(新添加)
Class.forName("com.ibm.db2.jdbc.net.DB2Driver");
String url="jdbc:db2://192.9.200.108:6789/SAMPLE"
cn = DriverManager.getConnection( url, sUsr, sPwd );
9.Microsoft SQL Server series (6.5, 7.x and 2000) and Sybase 10
JDBC Name: jTDS
URL: http://jtds.sourceforge.net/
Version: 0.5.1
Download URL: http://sourceforge.net/project/showfiles.php?group_id=33291
語法:
Class.forName("net.sourceforge.jtds.jdbc.Driver ");
Connection con = DriverManager.getConnection("jdbc:jtds:sqlserver://host:port/database","user","password");
or
Connection con = DriverManager.getConnection("jdbc:jtds:sybase://host:port/database","user","password");
10.Postgresql
JDBC Name: PostgreSQL JDBC
URL: http://jdbc.postgresql.org/
Version: 7.3.3 build 110
Download URL: http://jdbc.postgresql.org/download.html
語法:
Class.forName("org.postgresql.Driver");
Connection con=DriverManager.getConnection("jdbc:postgresql://host:port/database","user","password");
11.IBM AS400主機在用的JDBC語法
有裝V4R4以上版本的Client Access Express
可以在C:\Program Files\IBM\Client Access\jt400\lib
找到 driver 檔案 jt400.zip,并更改擴展名成為 jt400.jar
語法:
java.sql.DriverManager.registerDriver (new com.ibm.as400.access.AS400JDBCDriver ());
Class.forName("com.ibm.as400.access.AS400JDBCConnection");
con = DriverManager.getConnection("jdbc:as400://IP","user","password");
12.informix
Class.forName("com.informix.jdbc.IfxDriver").newInstance();
String url =
"jdbc:informix-sqli://123.45.67.89:1533/testDB:INFORMIXSERVER=myserver;
user=testuser;password=testpassword";
Lib:jdbcdrv.zip<br><br>Class.forName( "com.sybase.jdbc.SybDriver" )
url="jdbc:sybase:Tds:127.0.0.1:2638/asademo";
SybConnection connection= (SybConnection)DriverManager.getConnection(url,"dba","sql");
13.SAP DB
Class.forName ("com.sap.dbtech.jdbc.DriverSapDB");
java.sql.Connection connection = java.sql.DriverManager.getConnection ( "jdbc:sapdb://" + host + "/" + database_name,user_name, password)
14.InterBase
String url = "jdbc:interbase://localhost/e:/testbed/database/employee.gdb";
Class.forName("interbase.interclient.Driver");
//Driver d = new interbase.interclient.Driver (); /* this will also work if you do not want the line above */
Connection conn = DriverManager.getConnection( url, "sysdba", "masterkey" );
15.HSqlDB
url: http://hsqldb.sourceforge.net/
driver: org.hsqldb.jdbcDriver
連接方式有4種,分別為:
con-str(內存): jdbc:hsqldb.
con-str(本地): jdbc:hsqldb:/path/to/the/db/dir
con-str(http): jdbc:hsqldb:http://dbsrv
con-str(hsql): jdbc:hsqldb:hsql://dbsrv
posted @
2007-09-14 09:07 xzc 閱讀(320) |
評論 (1) |
編輯 收藏
var jobno number
begin
sys.dbms_job.submit(job => :jobno,
what => 'p_report_bb_install;',
next_date => to_date('05-09-2007', 'dd-mm-yyyy'),
interval => 'TRUNC(SYSDATE)+1');
commit;
end;
/
posted @
2007-09-04 17:42 xzc 閱讀(249) |
評論 (2) |
編輯 收藏
數據字典dict總是屬于Oracle用戶sys的。
1、用戶:
select username from dba_users;
改口令
alter user spgroup identified by spgtest;
2、表空間:
select * from dba_data_files;
select * from dba_tablespaces;//表空間
select tablespace_name,sum(bytes), sum(blocks)
from dba_free_space group by tablespace_name;//空閑表空間
select * from dba_data_files
where tablespace_name='RBS';//表空間對應的數據文件
select * from dba_segments
where tablespace_name='INDEXS';
3、數據庫對象:
select * from dba_objects;
CLUSTER、DATABASE LINK、FUNCTION、INDEX、LIBRARY、PACKAGE、PACKAGE BODY、
PROCEDURE、SEQUENCE、SYNONYM、TABLE、TRIGGER、TYPE、UNDEFINED、VIEW。
4、表:
select * from dba_tables;
analyze my_table compute statistics;->dba_tables后6列
select extent_id,bytes from dba_extents
where segment_name='CUSTOMERS' and segment_type='TABLE'
order by extent_id;//表使用的extent的信息。segment_type='ROLLBACK'查看回滾段的空間分配信息
列信息:
select distinct table_name
from user_tab_columns
where column_name='SO_TYPE_ID';
5、索引:
select * from dba_indexes;//索引,包括主鍵索引
select * from dba_ind_columns;//索引列
select i.index_name,i.uniqueness,c.column_name
from user_indexes i,user_ind_columns c
where i.index_name=c.index_name
and i.table_name ='ACC_NBR';//聯接使用
6、序列:
select * from dba_sequences;
7、視圖:
select * from dba_views;
select * from all_views;
text 可用于查詢視圖生成的腳本
8、聚簇:
select * from dba_clusters;
9、快照:
select * from dba_snapshots;
快照、分區應存在相應的表空間。
10、同義詞:
select * from dba_synonyms
where table_owner='SPGROUP';
//if owner is PUBLIC,then the synonyms is a public synonym.
if owner is one of users,then the synonyms is a private synonym.
11、數據庫鏈:
select * from dba_db_links;
在spbase下建數據庫鏈
create database link dbl_spnew
connect to spnew identified by spnew using 'jhhx';
insert into acc_nbr@dbl_spnew
select * from acc_nbr where nxx_nbr='237' and line_nbr='8888';
12、觸發器:
select * from dba_trigers;
存儲過程,函數從dba_objects查找。
其文本:select text from user_source where name='BOOK_SP_EXAMPLE';
建立出錯:select * from user_errors;
oracle總是將存儲過程,函數等軟件放在SYSTEM表空間。
13、約束:
(1)約束是和表關聯的,可在create table或alter table table_name add/drop/modify來建立、修改、刪除約束。
可以臨時禁止約束,如:
alter table book_example
disable constraint book_example_1;
alter table book_example
enable constraint book_example_1;
?。?)主鍵和外鍵被稱為表約束,而not null和unique之類的約束被稱為列約束。通常將主鍵和外鍵作為單獨的命名約束放在字段列表下面,而列約束可放在列定義的同一行,這樣更具有可讀性。
(3)列約束可從表定義看出,即describe;表約束即主鍵和外鍵,可從dba_constraints和dba_cons_columns 查。
select * from user_constraints
where table_name='BOOK_EXAMPLE';
select owner,CONSTRAINT_NAME,TABLE_NAME
from user_constraints
where constraint_type='R'
order by table_name;
?。?)定義約束可以無名(系統自動生成約束名)和自己定義約束名(特別是主鍵、外鍵)
如:create table book_example
(identifier number not null);
create table book_example
(identifier number constranit book_example_1 not null);
14、回滾段:
在所有的修改結果存入磁盤前,回滾段中保持恢復該事務所需的全部信息,必須以數據庫發生的事務來相應確定其大小(DML語句才可回滾,create,drop,truncate等DDL不能回滾)。
回滾段數量=并發事務/4,但不能超過50;使每個回滾段大小足夠處理一個完整的事務;
create rollback segment r05
tablespace rbs;
create rollback segment rbs_cvt
tablespace rbs
storage(initial 1M next 500k);
使回滾段在線
alter rollback segment r04 online;
用dba_extents,v$rollback_segs監測回滾段的大小和動態增長。
回滾段的區間信息
select * from dba_extents
where segment_type='ROLLBACK' and segment_name='RB1';
回滾段的段信息,其中bytes顯示目前回滾段的字節數
select * from dba_segments
where segment_type='ROLLBACK' and segment_name='RB1';
為事物指定回歸段
set transaction use rollback segment rbs_cvt
針對bytes可以使用回滾段回縮。
alter rollback segment rbs_cvt shrink;
select bytes,extents,max_extents from dba_segments
where segment_type='ROLLBACK' and segment_name='RBS_CVT';
回滾段的當前狀態信息:
select * from dba_rollback_segs
where segment_name='RB1';
比多回滾段狀態status,回滾段所屬實例instance_num
查優化值optimal
select n.name,s.optsize
from v$rollname n,v$rollstat s
where n.usn=s.usn;
回滾段中的數據
set transaction use rollback segment rb1;/*回滾段名*/
select n.name,s.writes
from v$rollname n,v$rollstat s
where n.usn=s.usn;
當事務處理完畢,再次查詢$rollstat,比較writes(回滾段條目字節數)差值,可確定事務的大小。
查詢回滾段中的事務
column rr heading 'RB Segment' format a18
column us heading 'Username' format a15
column os heading 'Os User' format a10
column te heading 'Terminal' format a10
select r.name rr,nvl(s.username,'no transaction') us,s.osuser os,s.terminal te
from v$lock l,v$session s,v$rollname r
where l.sid=s.sid(+)
and trunc(l.id1/65536)=R.USN
and l.type='TX'
and l.lmode=6
order by r.name;
15、作業
查詢作業信息
select job,broken,next_date,interval,what from user_jobs;
select job,broken,next_date,interval,what from dba_jobs;
查詢正在運行的作業
select * from dba_jobs_running;
使用包exec dbms_job.submit(:v_num,'a;',sysdate,'sysdate + (10/(24*60*60))')加入作業。間隔10秒鐘
exec dbms_job.submit(:v_num,'a;',sysdate,'sysdate + (11/(24*60))')加入作業。間隔11分鐘使用包exec dbms_job.remove(21)刪除21號作業。
posted @
2007-07-30 17:03 xzc 閱讀(227) |
評論 (0) |
編輯 收藏
一. Input和Output
1. stream代表的是任何有能力產出數據的數據源,或是任何有能力接收數據的接收源。在Java的IO中,所有的stream(包括Input和Out stream)都包括兩種類型:
1.1 以字節為導向的stream
以字節為導向的stream,表示以字節為單位從stream中讀取或往stream中寫入信息。以字節為導向的stream包括下面幾種類型:
1) input stream:
1) ByteArrayInputStream:把內存中的一個緩沖區作為InputStream使用
2) StringBufferInputStream:把一個String對象作為InputStream
3) FileInputStream:把一個文件作為InputStream,實現對文件的讀取操作
4) PipedInputStream:實現了pipe的概念,主要在線程中使用
5) SequenceInputStream:把多個InputStream合并為一個InputStream
2) Out stream
1) ByteArrayOutputStream:把信息存入內存中的一個緩沖區中
2) FileOutputStream:把信息存入文件中
3) PipedOutputStream:實現了pipe的概念,主要在線程中使用
4) SequenceOutputStream:把多個OutStream合并為一個OutStream
1.2 以Unicode字符為導向的stream
以Unicode字符為導向的stream,表示以Unicode字符為單位從stream中讀取或往stream中寫入信息。以Unicode字符為導向的stream包括下面幾種類型:
1) Input Stream
1) CharArrayReader:與ByteArrayInputStream對應
2) StringReader:與StringBufferInputStream對應
3) FileReader:與FileInputStream對應
4) PipedReader:與PipedInputStream對應
2) Out Stream
1) CharArrayWrite:與ByteArrayOutputStream對應
2) StringWrite:無與之對應的以字節為導向的stream
3) FileWrite:與FileOutputStream對應
4) PipedWrite:與PipedOutputStream對應
以字符為導向的stream基本上對有與之相對應的以字節為導向的stream。兩個對應類實現的功能相同,字是在操作時的導向不同。如CharArrayReader:和ByteArrayInputStream的作用都是把內存中的一個緩沖區作為InputStream使用,所不同的是前者每次從內存中讀取一個字節的信息,而后者每次從內存中讀取一個字符。
1.3 兩種不現導向的stream之間的轉換
InputStreamReader和OutputStreamReader:把一個以字節為導向的stream轉換成一個以字符為導向的stream。
2. stream添加屬性
2.1 “為stream添加屬性”的作用
運用上面介紹的Java中操作IO的API,我們就可完成我們想完成的任何操作了。但通過FilterInputStream和FilterOutStream的子類,我們可以為stream添加屬性。下面以一個例子來說明這種功能的作用。
如果我們要往一個文件中寫入數據,我們可以這樣操作:
FileOutStream fs = new FileOutStream(“test.txt”);
然后就可以通過產生的fs對象調用write()函數來往test.txt文件中寫入數據了。但是,如果我們想實現“先把要寫入文件的數據先緩存到內存中,再把緩存中的數據寫入文件中”的功能時,上面的API就沒有一個能滿足我們的需求了。但是通過FilterInputStream和FilterOutStream的子類,為FileOutStream添加我們所需要的功能。
2.2 FilterInputStream的各種類型
2.2.1 用于封裝以字節為導向的InputStream
1) DataInputStream:從stream中讀取基本類型(int、char等)數據。
2) BufferedInputStream:使用緩沖區
3) LineNumberInputStream:會記錄input stream內的行數,然后可以調用getLineNumber()和setLineNumber(int)
4) PushbackInputStream:很少用到,一般用于編譯器開發
2.2.2 用于封裝以字符為導向的InputStream
1) 沒有與DataInputStream對應的類。除非在要使用readLine()時改用BufferedReader,否則使用DataInputStream
2) BufferedReader:與BufferedInputStream對應
3) LineNumberReader:與LineNumberInputStream對應
4) PushBackReader:與PushbackInputStream對應
2.3 FilterOutStream的各種類型
2.2.3 用于封裝以字節為導向的OutputStream
1) DataIOutStream:往stream中輸出基本類型(int、char等)數據。
2) BufferedOutStream:使用緩沖區
3) PrintStream:產生格式化輸出
2.2.4 用于封裝以字符為導向的OutputStream
1) BufferedWrite:與對應
2) PrintWrite:與對應
3. RandomAccessFile
1) 可通過RandomAccessFile對象完成對文件的讀寫操作
2) 在產生一個對象時,可指明要打開的文件的性質:r,只讀;w,只寫;rw可讀寫
3) 可以直接跳到文件中指定的位置
4. I/O應用的一個例子
import java.io.*;
public class TestIO{
public static void main(String[] args)
throws IOException{
//1.以行為單位從一個文件讀取數據
BufferedReader in =
new BufferedReader(
new FileReader("F:\\nepalon\\TestIO.java"));
String s, s2 = new String();
while((s = in.readLine()) != null)
s2 += s + "\n";
in.close();
//1b. 接收鍵盤的輸入
BufferedReader stdin =
new BufferedReader(
new InputStreamReader(System.in));
System.out.println("Enter a line:");
System.out.println(stdin.readLine());
//2. 從一個String對象中讀取數據
StringReader in2 = new StringReader(s2);
int c;
while((c = in2.read()) != -1)
System.out.println((char)c);
in2.close();
//3. 從內存取出格式化輸入
try{
DataInputStream in3 =
new DataInputStream(
new ByteArrayInputStream(s2.getBytes()));
while(true)
System.out.println((char)in3.readByte());
}
catch(EOFException e){
System.out.println("End of stream");
}
//4. 輸出到文件
try{
BufferedReader in4 =
new BufferedReader(
new StringReader(s2));
PrintWriter out1 =
new PrintWriter(
new BufferedWriter(
new FileWriter("F:\\nepalon\\ TestIO.out")));
int lineCount = 1;
while((s = in4.readLine()) != null)
out1.println(lineCount++ + ":" + s);
out1.close();
in4.close();
}
catch(EOFException ex){
System.out.println("End of stream");
}
//5. 數據的存儲和恢復
try{
DataOutputStream out2 =
new DataOutputStream(
new BufferedOutputStream(
new FileOutputStream("F:\\nepalon\\ Data.txt")));
out2.writeDouble(3.1415926);
out2.writeChars("\nThas was pi:writeChars\n");
out2.writeBytes("Thas was pi:writeByte\n");
out2.close();
DataInputStream in5 =
new DataInputStream(
new BufferedInputStream(
new FileInputStream("F:\\nepalon\\ Data.txt")));
BufferedReader in5br =
new BufferedReader(
new InputStreamReader(in5));
System.out.println(in5.readDouble());
System.out.println(in5br.readLine());
System.out.println(in5br.readLine());
}
catch(EOFException e){
System.out.println("End of stream");
}
//6. 通過RandomAccessFile操作文件
RandomAccessFile rf =
new RandomAccessFile("F:\\nepalon\\ rtest.dat", "rw");
for(int i=0; i<10; i++)
rf.writeDouble(i*1.414);
rf.close();
rf = new RandomAccessFile("F:\\nepalon\\ rtest.dat", "r");
for(int i=0; i<10; i++)
System.out.println("Value " + i + ":" + rf.readDouble());
rf.close();
rf = new RandomAccessFile("F:\\nepalon\\ rtest.dat", "rw");
rf.seek(5*8);
rf.writeDouble(47.0001);
rf.close();
rf = new RandomAccessFile("F:\\nepalon\\ rtest.dat", "r");
for(int i=0; i<10; i++)
System.out.println("Value " + i + ":" + rf.readDouble());
rf.close();
}
}
關于代碼的解釋(以區為單位):
1區中,當讀取文件時,先把文件內容讀到緩存中,當調用in.readLine()時,再從緩存中以字符的方式讀取數據(以下簡稱“緩存字節讀取方式”)。
1b區中,由于想以緩存字節讀取方式從標準IO(鍵盤)中讀取數據,所以要先把標準IO(System.in)轉換成字符導向的stream,再進行BufferedReader封裝。
2區中,要以字符的形式從一個String對象中讀取數據,所以要產生一個StringReader類型的stream。
4區中,對String對象s2讀取數據時,先把對象中的數據存入緩存中,再從緩沖中進行讀取;對TestIO.out文件進行操作時,先把格式化后的信息輸出到緩存中,再把緩存中的信息輸出到文件中。
5區中,對Data.txt文件進行輸出時,是先把基本類型的數據輸出屋緩存中,再把緩存中的數據輸出到文件中;對文件進行讀取操作時,先把文件中的數據讀取到緩存中,再從緩存中以基本類型的形式進行讀取。注意in5.readDouble()這一行。因為寫入第一個writeDouble(),所以為了正確顯示。也要以基本類型的形式進行讀取。
6區是通過RandomAccessFile類對文件進行操作。
posted @
2007-06-20 21:49 xzc 閱讀(247) |
評論 (0) |
編輯 收藏
業務常用,供大家學習:
引用地址:http://www.easydone.cn/014/200604022353065155.htm
package org.easydone.file;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.io.PrintWriter;
import java.text.SimpleDateFormat;
import java.util.Date;
/**
* <p>Title: File 常用操作(部分)</p>
* <p>Description: 業務用</p>
* <p>Copyright: Copyright (c) 2006
www.easydone.cn</p>
* <p>Company: 北京聚能易成科技有限公司</p>
* @authory dirboy
* @version 1.0
*/
public class FileOperate {
/**
* 創建目錄
* @param folderPath:目錄路徑
* @return
* @throws IOException
*/
public static boolean createFolder(String folderPath) throws IOException {
boolean result = false;
File f = new File(folderPath);
result = f.mkdirs();
return result;
}
/**
* 刪除目錄下所有文件
* @param directory (File 對象)
*/
public void emptyDirectory(File directory) {
File[] entries = directory.listFiles();
for (int i = 0; i < entries.length; i++) {
entries[i].delete();
}
}
/**
* 創建文件
* @param filepath:文件所在目錄路徑,比如:c:/test/test.txt
* @return
*/
public static boolean makeFile(String filepath) throws IOException {
boolean result = false;
File file = new File(filepath);
result = file.createNewFile();
file = null;
return result;
}
/**
* 刪除文件
* @param filepath:文件所在物理路徑
* @return
*/
public static boolean isDel(String filepath) {
boolean result = false;
File file = new File(filepath);
result = file.delete();
file = null;
return result;
}
/**
* 文件重命名
* @param filepath:文件所在物理路徑
* @param destname:新文件名
* @return
*/
public static boolean renamefile(String filepath,String destname) {
boolean result = false;
File f = new File(filepath);
String fileParent = f.getParent();
String filename = f.getName();
File rf = new File(fileParent+"http://"+destname);
if(f.renameTo(rf)) {
result = true;
}
f = null;
rf = null;
return result;
}
/**
* 將文件內容寫入數據庫中
* @param filepath:文件所在物理路徑
* @param content:寫入內容
* @throws Exception
*/
public static void WriteFile(String filepath,String content) throws Exception {
FileWriter filewriter = new FileWriter(filepath,true);//寫入多行
PrintWriter printwriter = new PrintWriter(filewriter);
printwriter.println(content);
printwriter.flush();
printwriter.close();
filewriter.close();
}
/**
* 日志備份
* @param filePath:日志備份路徑
* @param baksize:日志備份大小參考值(字節大小)
* @throws IOException
*/
public static void logBak(String filePath,long baksize) throws IOException {
File f = new File(filePath);
long len = f.length();
SimpleDateFormat simpledateformat = new SimpleDateFormat("yyyyMMddHHmmss");
String s = simpledateformat.format(new Date());
String fileName = f.getName();
int dot = fileName.indexOf(".");
String bakName = s+fileName.substring(dot);
System.out.println(bakName);
if(len>=baksize) {
renamefile(filePath,bakName);
makeFile(filePath);
}
f = null;
}
}
posted @
2007-06-14 16:52 xzc 閱讀(2060) |
評論 (0) |
編輯 收藏
摘要:收集一些常用的正則表達式。
正則表達式用于字符串處理,表單驗證等場合,實用高效,但用到時總是不太把握,以致往往要上網查一番。我將一些常用的表達式收藏在這里,作備忘之用。本貼隨時會更新。
匹配中文字符的正則表達式:
匹配雙字節字符(包括漢字在內):
應用:計算字符串的長度(一個雙字節字符長度計2,ASCII字符計1)
String
.
prototype
.
len
=
function
(){
return
this
.
replace
([
^\
x00
-\
xff
]
/
g,"aa").length; }
匹配空行的正則表達式:
匹配HTML標記的正則表達式:
/
<(.*)>.*<
\/
\1>|<(.*)
\/
>
/
匹配首尾空格的正則表達式:
應用:j avascript中沒有像v bscript那樣的trim函數,我們就可以利用這個表達式來實現,如下:
String
.
prototype
.
trim
=
function
()
{
?? ?
return
this
.
replace
(
/
(^\s*)|(\s*$)
/g
,
""
)
;
}
利用正則表達式分解和轉換IP地址
下面是利用正則表達式匹配IP地址,并將IP地址轉換成對應數值的Javascript程序:
function
IP2V
(
ip
)
{
?? ?
re
=
/
(\d+)\.(\d+)\.(\d+)\.(\d+)
/g
?
//匹配IP地址的正則表達式
?? ?
if
(
re
.
test
(
ip
))
?? ?
{
?? ? ? ?
return
RegExp
.$
1
*
Math
.
pow
(
255
,
3
)
)+
RegExp
.$
2
*
Math
.
pow
(
255
,
2
)
)+
RegExp
.$
3
*
255
+
RegExp
.$
4
*
1
?? ?
}
?? ?
else
?? ?
{
?? ? ? ?
throw
new
Error
(
"
Not a valid IP address!
"
)
?? ?
}
}
不過上面的程序如果不用正則表達式,而直接用split函數來分解可能更簡單,程序如下:
var
ip
=
"
10.100.20.168
"
ip
=
ip
.
split
(
"
.
"
)
alert
(
"
IP值是:
"
+
(
ip
[
0
]
*
255
*
255
*
255
+
ip
[
1
]
*
255
*
255
+
ip
[
2
]
*
255
+
ip
[
3
]
*
1
))
匹配Email地址的正則表達式:
\
w
+
([
-+.
]
\
w
+
)
*@\
w
+
([
-.
]
\
w
+
)
*\.\
w
+
([
-.
]
\
w
+
)
*
匹配網址URL的正則表達式:
http
:
//([\w-]+\.)+[\w-]+(/[\w- ./?%&=]*)?
利用正則表達式去除字串中重復的字符的算法程序:[*注:此程序不正確]
var
s
=
"
abacabefgeeii
"
var
s1
=
s
.
replace
(
/
(.).*\1
/g
,
"
$1
"
)
var
re
=
new
RegExp
(
"
[
"
+
s1
+
"
]
"
,
"
g
"
)
var
s2
=
s
.
replace
(
re
,
""
)
alert
(
s1
+
s2
)
?
//結果為:abcefgi
*注
===============================
如果var s = “abacabefggeeii”
結果就不對了,結果為:abeicfgg
正則表達式的能力有限
===============================
我原來在CSDN上發貼尋求一個表達式來實現去除重復字符的方法,最終沒有找到,這是我能想到的最簡單的實現方法。思路是使用后向引用取出包括重復的字符,再以重復的字符建立第二個表達式,取到不重復的字符,兩者串連。這個方法對于字符順序有要求的字符串可能不適用。
得用正則表達式從URL地址中提取文件名的javascript程序,如下結果為page1
s
=
"
http://blog.penner.cn/page1.htm
"
s
=
s
.
replace
(
/
(.*
\/
){ 0, }([^\.]+).*
/i
g
,
"
$2
"
)
alert
(
s
)
利用正則表達式限制網頁表單里的文本框輸入內容:
用正則表達式限制只能輸入中文:
onkeyup
=
"
value=value.replace(/[^\u4E00-\u9FA5]/g,'')
"
onbeforepaste
=
"
clipboardData.setData('text',clipboardData.getData('text').replace(/[^\u4E00-\u9FA5]/g,''))
"
用正則表達式限制只能輸入全角字符:
onkeyup
=
"
value=value.replace(/[^\uFF00-\uFFFF]/g,'')
"
onbeforepaste
=
"
clipboardData.setData('text',clipboardData.getData('text').replace(/[^\uFF00-\uFFFF]/g,''))
"
用正則表達式限制只能輸入數字:
onkeyup
=
"
value=value.replace(/[^\d]/g,'')
"
onbeforepaste
=
"
clipboardData.setData('text',clipboardData.getData('text').replace(/[^\d]/g,''))
"
用正則表達式限制只能輸入數字和英文:
onkeyup
=
"
value=value.replace(/[\W]/g,'')
"
onbeforepaste
=
"
clipboardData.setData('text',clipboardData.getData('text').replace(/[^\d]/g,''))
"
匹配非負整數(正整數 + 0)
匹配正整數
^
[
0
-
9
]
*
[
1
-
9
][
0
-
9
]
*$
匹配非正整數(負整數 + 0)
^
((
-\
d
+
)
|
(
0
+
))
$
匹配負整數
^-
[
0
-
9
]
*
[
1
-
9
][
0
-
9
]
*$
匹配整數
匹配非負浮點數(正浮點數 + 0)
匹配正浮點數
^
(([
0
-
9
]
+\.
[
0
-
9
]
*
[
1
-
9
][
0
-
9
]
*
)
|
([
0
-
9
]
*
[
1
-
9
][
0
-
9
]
*\.
[
0
-
9
]
+
)
|
([
0
-
9
]
*
[
1
-
9
][
0
-
9
]
*
))
$
匹配非正浮點數(負浮點數 + 0)
^
((
-\
d
+
(
\.\
d
+
)
?
)
|
(
0
+
(
\
.0
+
)
?
))
$
匹配負浮點數
^
(
-
(([
0
-
9
]
+\.
[
0
-
9
]
*
[
1
-
9
][
0
-
9
]
*
)
|
([
0
-
9
]
*
[
1
-
9
][
0
-
9
]
*\.
[
0
-
9
]
+
)
|
([
0
-
9
]
*
[
1
-
9
][
0
-
9
]
*
)))
$
匹配浮點數
^
(
-?\
d
+
)(
\.\
d
+
)
?$
匹配由26個英文字母組成的字符串
匹配由26個英文字母的大寫組成的字符串
匹配由26個英文字母的小寫組成的字符串
匹配由數字和26個英文字母組成的字符串
匹配由數字、26個英文字母或者下劃線組成的字符串
匹配email地址
^
[
\
w
-
]
+
(
\.
[
\
w
-
]
+
)
*@
[
\
w
-
]
+
(
\.
[
\
w
-
]
+
)
+$
匹配url
^
[
a
-
zA
-
z
]
+:
//匹配(\w+(-\w+)*)(\.(\w+(-\w+)*))*(\?\S*)?$
匹配html tag
<\
s
*
(
\
S
+
)(
\
s
[
^>
]
*
)
?>
(
.*?
)
<\
s
*\
/
\1\s*>
Visual Basic & C# Regular Expression
1.確認有效電子郵件格式
下面的示例使用靜態 Regex.IsMatch 方法驗證一個字符串是否為有效電子郵件格式。如果字符串包含一個有效的電子郵件地址,則 IsValidEmail 方法返回 true,否則返回 false,但不采取其他任何操作。您可以使用 IsValidEmail,在應用程序將地址存儲在數據庫中或顯示在 ASP.NET 頁中之前,篩選出包含無效字符的電子郵件地址。
[Visual Basic]
Function IsValidEmail(strIn As String) As Boolean
' Return true if strIn is in valid e-mail format.
Return Regex.IsMatch(strIn, ("^([\w-\.]+)@((\[[0-9]{ 1,3 }\.[0-9]{ 1,3 }\.[0-9]{ 1,3 }\.)|(([\w-]+\.)+))([a-zA-Z]{ 2,4 }|[0-9]{ 1,3 })(\]?)$")
End Function
[C#]
bool IsValidEmail(string strIn)
{
// Return true if strIn is in valid e-mail format.
return Regex.IsMatch(strIn, @"^([\w-\.]+)@((\[[0-9]{ 1,3 }\.[0-9]{ 1,3 }\.[0-9]{ 1,3 }\.)|(([\w-]+\.)+))([a-zA-Z]{ 2,4 }|[0-9]{ 1,3 })(\]?)$");
}
2.清理輸入字符串
下面的代碼示例使用靜態 Regex.Replace 方法從字符串中抽出無效字符。您可以使用這里定義的 CleanInput 方法,清除掉在接受用戶輸入的窗體的文本字段中輸入的可能有害的字符。CleanInput 在清除掉除 @、-(連字符)和 .(句點)以外的所有非字母數字字符后返回一個字符串。
[Visual Basic]
Function CleanInput(strIn As String) As String
' Replace invalid characters with empty strings.
Return Regex.Replace(strIn, "[^\w\.@-]", "")
End Function
[C#]
String CleanInput(string strIn)
{
?? ?// Replace invalid characters with empty strings.
?? ?return Regex.Replace(strIn, @"[^\w\.@-]", "");
}
3.更改日期格式
以下代碼示例使用 Regex.Replace 方法來用 dd-mm-yy 的日期形式代替 mm/dd/yy 的日期形式。
[Visual Basic]
Function MDYToDMY(input As String) As String
Return Regex.Replace(input, _
"\b(?<month>\d{ 1,2 })/(?<day>\d{ 1,2 })/(?<year>\d{ 2,4 })\b", _
"${ day }-${ month }-${ year }")
End Function
[C#]
String MDYToDMY(String input)
{
?? ?return Regex.Replace(input,"\\b(?<month>\\d{ 1,2 })/(?<day>\\d{ 1,2 })/(?<year>\\d{ 2,4 })\\b","${ day }-${ month }-${ year }");
}
Regex 替換模式
本示例說明如何在 Regex.Replace 的替換模式中使用命名的反向引用。其中,替換表達式 ${ day } 插入由 (?…) 組捕獲的子字符串。
有幾種靜態函數使您可以在使用正則表達式操作時無需創建顯式正則表達式對象,而 Regex.Replace 函數正是其中之一。如果您不想保留編譯的正則表達式,這將給您帶來方便
4.提取 URL 信息
以下代碼示例使用 Match.Result 來從 URL 提取協議和端口號。例如,“http://www.penner.cn:8080……將返回“http:8080”。
[Visual Basic]
Function Extension(url As String) As String
Dim r As New Regex("^(?<proto>\w+)://[^/]+?(?<port>:\d+)?/", _
RegexOptions.Compiled)
Return r.Match(url).Result("${ proto }${ port }")
End Function
[C#]
String Extension(String url)
{
?? ?Regex r = new Regex(@"^(?<proto>\w+)://[^/]+?(?<port>:\d+)?/",
?? ?RegexOptions.Compiled);
?? ?return r.Match(url).Result("${ proto }${ port }");
}
只有字母和數字,不小于6位,且數字字母都包含的密碼的正則表達式
在C#中,可以用這個來表示:
一個將需要將路徑字符串拆分為根目錄和子目錄兩部分的算法程序,考慮路徑格式有:C:\aa\bb\cc ,\\aa\bb\cc , ftp://aa.bb/cc 上述路徑將分別被拆分為:C:\和aa\bb\cc ,\\aa 和 \bb\cc , ftp:// 和 aa.bb/cc 用javascript實現如下:
var
strRoot
,
strSub
var
regPathParse
=
/
^([^\\^
\/
]+[\\
\/
]+|\\\\[^\\]+)(.*)$
/
if
(
regPathParse
.
test
(
strFolder
))
{
?? ?
strRoot
=
RegExp
.$
1
?? ?
strSub
=
RegExp
.$
2
}
Tags:?
JavaScript?正則表達式?This entry was posted on 星期二, 三月 22nd, 2005 at 11:12:25 and is filed under Tech, JavaScript. You can follow any responses to this entry through the RSS 2.0 feed. You can leave a response, or trackback from your own site.
posted @
2007-03-16 17:08 xzc 閱讀(450) |
評論 (0) |
編輯 收藏
Selenium備忘手冊
??? 最近的項目準備用Selenium作一部分的Regression Test。在SpringSide里參考了一下,又下了個Selenium IDE玩玩,覺得還蠻容易上手,基本上不需要手動寫測試代碼。
??? 但實操起來時面對各種復雜的頁面情況遇到不少麻煩。感覺Selenium 的offical documentation寫的比較high level, 最后找了個though works的ppt,算得上比較全面易懂。匆匆翻譯了一下,供后來者參考。
一、?格式
1.?Test Case 格式
? |
?Title |
? |
?命令(Command)? |
?目標(Target)? |
?值(Value) |
?命令(Command) |
?目標(Target)? |
??( ) |
?判斷(Assertion)? |
?期望值(Expected)? |
?實際值(Actual) |
2.?Test Suites 格式
?Title |
?TestCase1.html |
?TestCase2.html |
?TestCase3.html |
二、?Commands (命令)
-
Action
對當前狀態進行操作
失敗時,停止測試
-
Assertion
校驗是否有產生正確的值
-
Element Locators
指定HTML中的某元素
-
Patterns
用于模式匹配
1.?Element Locators (元素定位器)
-
id=id
id locator 指定HTML中的唯一id的元素?
-
?name=name
name locator指定 HTML中相同name的元素中的第一個元素
-
?identifier=id
identifier locator 首先查找HTML是否存在該id的元素, 若不存在,查找第一個該name的元素?
-
dom=javascriptExpression
dom locator用JavaScript表達式來定位HTML中的元素,注意必須要以”document”開頭
例如:
dom=document.forms[‘myForm’].myDropdown
dom=document.images[56]
-
?xpath=xpathExpression
xpath locator用 XPath 表達式來定位HTML中的元素,必須注意要以”//”開頭
例如:
xpath=//img[@alt=’The image alt text’]
xpath=//table[@id=’table1’]//tr[4]/td[2]
-
?link=textPattern
link locator 用link來選擇HTML中的連接或錨元素
例如:
link=The link text
- 在沒有locator前序的情況下 Without a locator prefix, Selenium uses:
如果以”document.”開頭,則默認是使用 dom locator,如果是以“//”開頭,則默認使用xpath locator,其余情況均認作identifier locator
2.?String Matching Patterns (字符串匹配模式)
-
glob:patthern
glob模式,用通配符”*”代表任意長度字符,“?”代表一個字符
-
regexp:regexp
正則表達式模式,用JavaScript正則表達式的形式匹配字符串
-
exact:string
精確匹配模式,精確匹配整個字符串,不能用通配符
- 在沒有指定字符串匹配前序的時候,selenium 默認使用golb 匹配模式
3.?Select Option Specifiers (Select選項指定器)
-
label=labelPattern
通過匹配選項中的文本指定選項
例如:label=regexp:^[Oo]ther
-
value=valuePattern
通過匹配選項中的值指定選項
例如:value=other
-
id=id
通過匹配選項的id指定選項
例如: id=option1
-
index=index
通過匹配選項的序號指定選項,序號從0開始
例如:index=2
- 在沒有選項選擇前序的情況下,默認是匹配選項的文本
三、?Actions
描述了用戶所會作出的操作。
Action 有兩種形式: action和actionAndWait, action會立即執行,而actionAndWait會假設需要較長時間才能得到該action的相響,而作出等待,open則是會自動處理等待時間。
-
click
click(elementLocator)
-?點擊連接,按鈕,復選和單選框
-?如果點擊后需要等待響應,則用”clickAndWait”
-?如果是需要經過JavaScript的alert或confirm對話框后才能繼續操作,則需要調用verify或assert來告訴Selenium你期望對對話框進行什么操作。
?click | ?aCheckbox | ? |
?clickAndWait | ?submitButton | ? |
?clickAndWait? | ?anyLink | ? |
-
open
open(url)
-?在瀏覽器中打開URL,可以接受相對和絕對路徑兩種形式
-?注意:該URL必須在與瀏覽器相同的安全限定范圍之內
-
type
?type(inputLocator, value)
-?模擬人手的輸入過程,往指定的input中輸入值
-?也適合給復選和單選框賦值
-?在這個例子中,則只是給鉤選了的復選框賦值,注意,而不是改寫其文本
?type | ?nameField? | ?John Smith |
?typeAndWait? | ?textBoxThatSubmitsOnChange | ?newValue |
-
select
select(dropDownLocator, optionSpecifier)
-?根據optionSpecifier選項選擇器來選擇一個下拉菜單選項
-?如果有多于一個選擇器的時候,如在用通配符模式,如”f*b*”,或者超過一個選項有相同的文本或值,則會選擇第一個匹配到的值
?select?? | ?dropDown? | ?Australian Dollars |
?select?? | ?dropDown | ??index=0 |
?selectAndWait? | ?currencySelector? | ?value=AUD |
?selectAndWait? | ?currencySelector? | ?label=Auslian D*rs |
- ?goBack,close
goBack()
模擬點擊瀏覽器的后退按鈕
close()
模擬點擊瀏覽器關閉按鈕
-
selectWindow
select(windowId)
-?選擇一個彈出窗口
-?當選中那個窗口的時候,所有的命令將會轉移到那窗口中執行
?selectWindow? | ?myPopupWindow | ? |
?selectWindow | ?null | ? |
-
pause
pause(millisenconds)
-?根據指定時間暫停Selenium腳本執行
-?常用在調試腳本或等待服務器段響應時
?pause? | ?5000 | ? |
?pause? | ?2000 | ? |
-
fireEvent
?fireEvent(elementLocatore,evenName)
模擬頁面元素事件被激活的處理動作
?fireEvent? | ?textField | focus? |
?fireEvent | ?dropDown | ?blur |
-
waitForCondition
waitForCondition(JavaScriptSnippet,time)
- 在限定時間內,等待一段JavaScript代碼返回true值,超時則停止等待
?waitForCondition? | ?var value=selenium.getText("foo"); value.match(/bar/); | ?3000 |
-
waitForValue
waitForValue(inputLocator, value)
-?等待某input(如hidden input)被賦予某值,
-?會輪流檢測該值,所以要注意如果該值長時間一直不賦予該input該值的話,可能會導致阻塞
?waitForValue | ?finishIndication | isfinished? |
? | ? | ? |
-
store,stroreValue
store(valueToStore, variablename)
保存一個值到變量里。
該值可以由自其他變量組合而成或通過JavaScript表達式賦值給變量
?store? | ?Mr John Smith | ?fullname |
?store? | ?${title} ${firstname} ${suname} | ?fullname |
?store? | ?javascript{Math.round(Math.PI*100)/100} | ?PI |
?storeValue | ?inputLocator | ?variableName |
把指定的input中的值保存到變量中
?storeValue? | ?userName? | userID? |
?type? | ?userName? | ?${userID} |
-
storeText, storeAttribute
storeText(elementLocator, variablename)
把指定元素的文本值賦予給變量
?storeText? | ?currentDate? | ?expectedStartDate |
?verifyValue? | ?startDate? | ?${expectedStartDate} |
storeAttribute(elementLocator@attributeName,variableName)
把指定元素的屬性的值賦予給變量
?storeAttribute? | input1@class?? | ?classOfInput1 |
?verifyAttribute? | ?input2@class? | ?${classOfInput1} |
-
chooseCancel.., answer..
chooseCancelOnNextConfirmation()
-?當下次JavaScript彈出confirm對話框的時候,讓selenium選擇Cancel
-?如果沒有該命令時,遇到confirm對話框Selenium默認返回true,如手動選擇OK按鈕一樣
?chooseCancelOnNextConfirmation?? | ? | ? |
-?如果已經運行過該命令,當下一次又有confirm對話框出現時,也會同樣地再次選擇Cancel
answerOnNextPrompt(answerString)
- 在下次JavaScript彈出prompt提示框時,賦予其anweerString的值,并選擇確定
?answerOnNextPrompt? | ?Kangaroo? | ? |
四、?Assertions
允許用戶去檢查當前狀態。兩種模式: Assert 和 Verify,?當Assert失敗,則退出測試;當Verify失敗,測試會繼續運行。
-
assertLocation, assertTitle
assertLocation(relativeLocation)
判斷當前是在正確的頁面
?verifyLocation? | ?/mypage | ? |
?assertLocation? | ?/mypage | ? |
-
assertTitle(titlePattern)
檢查當前頁面的title是否正確
?verifyTitle? | ?My Page? | ? |
?assertTitle? | ?My Page? | ? |
-
assertValue
assertValue(inputLocator, valuePattern)
-?檢查input的值
-?對于 checkbox或radio,如果已選擇,則值為”on”,反之為”off”
?verifyValue? | ?nameField? | ?John Smith |
?assertValue? | ?document.forms[2].nameField | ?John Smith |
-
assertSelected, assertSelectedOptions
assertSelected(selectLocator, optionSpecifier)
檢查select的下拉菜單中選中的選型是否和optionSpecifer(Select選擇選項器)的選項相同
?verifySelected? | ?dropdown2? | ?John Smith |
?verifySelected? | ?dorpdown2? | ?value=js*123 |
?assertSelected? | ?document.forms[2].dropDown | ?label=J*Smith |
?assertSelected? | ?document.forms[2].dropDown? | ?index=0 |
-
assertSelectOptions(selectLocator, optionLabelList)
-?檢查下拉菜單中的選項的文本是否和optionLabelList相同
-?optionLabelList是以逗號分割的一個字符串
?verifySelectOptions? | ?dropdown2? | ?John Smith,Dave Bird |
?assertSelectOptions? | ?document.forms[2].dropdown | ?Smith,J,Bird,D |
-
assertText
assertText(elementLocator,textPattern)
-?檢查指定元素的文本
-?只對有包含文本的元素生效
-?對于Mozilla類型的瀏覽器,用textContent取元素的文本,對于IE類型的瀏覽器,用innerText取元素文本
?verifyText? | ?statusMessage? | ?Successful |
?assertText? | ?//div[@id='foo']//h1 | ?Successful |
?
-
assertTextPresent, assertAttribute
assertTextPresent(text)
檢查在當前給用戶顯示的頁面上是否有出現指定的文本
?verifyTextPresent? | ?You are now logged in? | ? |
?assertTextPresent? | ?You are now logged in? | ? |
-
assertAttribute(
elementLocator@attributeName
, ValuePattern)
檢查當前指定元素的屬性的值
?verifyAttribute? | txt1@class | ?bigAndBlod |
?assertAttribute? | ?document.images[0]@alt | ?alt-text |
?verifyAttribute? | ?//img[@id='foo']/alt? | ?alt-text |
-
assertTextPresent, etc.
assertTextPresent(text)
assertTextNotPresent(text)
assertElementPresent(elementLocator)
?verifyElementPresent? | ?submitButton? | ? |
?assertElementPresent? | ?//img[@alt='foo']? | ? |
assertElementNotPresent(elementLocator)
-
assertTable
assertTable(cellAddress, valuePattern)
-?檢查table里的某個cell中的值
-?cellAddress的語法是tableName.row.column, 注意行列序號都是從0開始
?verifyTable? | ?myTable.1.6 | ?Submitted |
?assertTable? | ?results0.2? | ?13 |
?
-
assertVisible, nonVisible
assertVisible(elementLocator)
-?檢查指定的元素是否可視的
-?隱藏一個元素可以用設置css的‘visibility’屬性為’hidden’,也可以設置‘display’屬性為‘none’
?verfyVisible? | ?postcode? | ? |
?assertVisible? | ?postcode? | ? |
-
assertNotVisible(elementLocator)
?verfyNotVisible? | ?postcode? | ? |
?assertNotVisible? | ?postcode? | ? |
-
Editable, non-editable
assertEditable(inputLocator)
檢查指定的input是否可以編輯
?verifyEditable? | ?shape? | ? |
?assertEditable? | ?colour? | ? |
-
assertNotEditable(inputLocator)
檢查指定的input是否不可以編輯
-
assertAlert
assertAlert(messagePattern)
-?檢查JavaScript是否有產生帶指定message的alert對話框
-?alert產生的順序必須與檢查的順序一致
-?檢查alert時會產生與手動點擊’OK’按鈕一樣的效果。如果一個alert產生了,而你卻沒有去檢查它,selenium會在下個action中報錯。
-?注意:Selenium 不支持 JavaScript 在onload()事件時 調用alert();在這種情況下,Selenium需要你自己手動來點擊OK.
-
assertConfirmation
assertConfirmation(messagePattern)
-?檢查JavaScript是否有產生帶指定message的confirmation對話框和alert情況一樣,confirmation對話框也必須在它們產生的時候進行檢查
-?默認情況下,Selenium會讓confirm() 返回true, 相當于手動點擊Ok按鈕的效果。你能夠通過chooseCancelOnNextConfirmation命令讓confirm()返回false.同樣地,如果一個cofirmation對話框出現了,但你卻沒有檢查的話,Selenium將會在下個action中報錯
-?注意:在Selenium的環境下,confirmation對話框框將不會再出現彈出顯式對話框
-?注意:Selenium不支持在onload()事件時調用confirmation對話框,在這種情況下,會出現顯示confirmatioin對話框,并需要你自己手動點擊。
-
?assertPrompt
assertPrompt(messagePattern)
-?檢查JavaScript是否有產生帶指定message的Prompt對話框
-?你檢查的prompt的順序Prompt對話框產生的順序必須相同
-?必須在verifyPrompt之前調用answerOnNextPrompt命令
-?如果prompt對話框出現了但你卻沒有檢查,則Selenium會在下個action中報錯
?answerOnNextPrompt? | ?Joe? | ? |
?click? | ?id=delegate? | ? |
?verifyPrompt? | ?Delegate to who?? | ? |
五、?Parameters and Variables
參數和變量的聲明范圍由簡單的賦值到JavaScript表達式賦值。
Store,storeValue 和storeText 為下次訪問保存值。
在Selenium內部是用一個叫storeVars的map來保存變量名。
-
Variable Substitution 變量替換
提供了一個簡單的方法去訪問變量,語法 ${xxx}
?store? | ??Mr? | ?title |
?storeValue? | ?nameField? | ?surname |
?store? | ??${title} ${suname} | ?fullname |
?type? | ?textElement? | ?Full name is: ${fullname} |
-
?JavaScript Evaluation JavaScript賦值
你能用JavaScript來構建任何你所需要的值。
這個參數是以javascript開頭,語法是 javascript{‘with a trailing’}。
可以通過JavaScript表達式給某元素賦值。
store? | ?javascript{'merchant'+(new Date()).getTime()}? | ?merchantId |
?type? | textElement? | ?javascript{storedVars['merchantId'].toUpperCase()} |
-
Generating Unique values 產生唯一值. ?
問題:你需要唯一的用戶名
解決辦法: 基于時間來產生用戶名,如’fred’+(new Date().getTime())
posted @
2007-02-12 10:49 xzc 閱讀(2066) |
評論 (1) |
編輯 收藏
作者:Radic 來源:sun
摘要:
本文是來自Sun官方站點的一篇關于如何編寫安全的Java代碼的指南,開發者在編寫一般代碼時,可以參照本文的指南
本文是來自Sun官方站點的一篇關于如何編寫安全的Java代碼的指南,開發者在編寫一般代碼時,可以參照本文的指南:
• 靜態字段
• 縮小作用域
• 公共方法和字段
• 保護包
• equals方法
• 如果可能使對象不可改變
• 不要返回指向包含敏感數據的內部數組的引用
• 不要直接存儲用戶提供的數組
• 序列化
• 原生函數
• 清除敏感信息靜態字段• 避免使用非final的公共靜態變量
應盡可能地避免使用非final公共靜態變量,因為無法判斷代碼有無權限改變這些變量值。
• 一般地,應謹慎使用易變的靜態狀態,因為這可能導致設想中相互獨立的子系統之間發生不可預知的交互。
縮小作用域作為一個慣例,盡可能縮小方法和字段的作用域。檢查包訪問權限的成員能否改成私有的,保護類型的成員可否改成包訪問權限的或者私有的,等等。
公共方法/字段避免使用公共變量,而是使用訪問器方法訪問這些變量。用這種方式,如果需要,可能增加集中安全控制。
對于任何公共方法,如果它們能夠訪問或修改任何敏感內部狀態,務必使它們包含安全控制。
參考如下代碼段,該代碼段中不可信任代碼可能設置TimeZone的值:
private static TimeZone defaultZone = null;
public static synchronized void setDefault(TimeZone zone)
{
defaultZone = zone;
}
保護包有時需要在全局防止包被不可信任代碼訪問,本節描述了一些防護技術:
• 防止包注入:如果不可信任代碼想要訪問類的包保護成員,可以嘗試在被攻擊的包內定義自己的新類用以獲取這些成員的訪問權。防止這類攻擊的方式有兩種:
1. 通過向java.security.properties文件中加入如下文字防止包內被注入惡意類。
...
package.definition=Package#1 [,Package#2,...,Package#n]
...
這會導致當試圖在包內定義新類時類裝載器的defineClass方法會拋出異常,除非賦予代碼一下權限:
...
RuntimePermission("defineClassInPackage."+package)
...
2. 另一種方式是通過將包內的類加入到封裝的Jar文件里。
(參看http://java.sun.com/j2se/sdk/1.2/docs/guide/extensions/spec.html)
通過使用這種技巧,代碼無法獲得擴展包的權限,因此也無須修改java.security.properties文件。
• 防止包訪問:通過限制包訪問并僅賦予特定代碼訪問權限防止不可信任代碼對包成員的訪問。通過向java.security.properties文件中加入如下文字可以達到這一目的:
...
package.access=Package#1 [,Package#2,...,Package#n]
...
這會導致當試圖在包內定義新類時類裝載器的defineClass方法會拋出異常,除非賦予代碼一下權限:
...
RuntimePermission("defineClassInPackage."+package)
...
如果可能使對象不可改變如果可能,使對象不可改變。如果不可能,使得它們可以被克隆并返回一個副本。如果返回的對象是數組、向量或哈希表等,牢記這些對象不能被改變,調用者修改這些對象的內容可能導致安全漏洞。此外,因為不用上鎖,不可改變性能夠提高并發性。參考Clear sensitive information了解該慣例的例外情況。
不要返回指向包含敏感數據的內部數組的引用該慣例僅僅是不可變慣例的變型,在這兒提出是因為常常在這里犯錯。即使數組中包含不可變的對象(如字符串),也要返回一個副本這樣調用者不能修改數組中的字符串。不要傳回一個數組,而是數組的拷貝。
不要直接在用戶提供的數組里存儲該慣例僅僅是不可變慣例的另一個變型。使用對象數組的構造器和方法,比如說PubicKey數組,應當在將數組存儲到內部之前克隆數組,而不是直接將數組引用賦給同樣類型的內部變量。缺少這個警惕,用戶對外部數組做得任何變動(在使用討論中的構造器創建對象后)可能意外地更改對象的內部狀態,即使該對象可能是無法改變的
序列化當對對象序列化時,直到它被反序列化,它不在Java運行時環境的控制之下,因此也不在Java平臺提供的安全控制范圍內。
在實現Serializable時務必將以下事宜牢記在心:
• transient
在包含系統資源的直接句柄和相對地址空間信息的字段前使用transient關鍵字。 如果資源,如文件句柄,不被聲明為transient,該對象在序列化狀態下可能會被修改,從而使得被反序列化后獲取對資源的不當訪問。
• 特定類的序列化/反序列化方法
為了確保反序列化對象不包含違反一些不變量集合的狀態,類應該定義自己的反序列化方法并使用ObjectInputValidation接口驗證這些變量。
如果一個類定義了自己的序列化方法,它就不能向任何DataInput/DataOuput方法傳遞內部數組。所有的DataInput/DataOuput方法都能被重寫。注意默認序列化不會向DataInput/DataOuput字節數組方法暴露私有字節數組字段。
如果Serializable類直接向DataOutput(write(byte [] b))方法傳遞了一個私有數組,那么黑客可以創建ObjectOutputStream的子類并覆蓋write(byte [] b)方法,這樣他可以訪問并修改私有數組。下面示例說明了這個問題。
你的類:
public class YourClass implements Serializable {
private byte [] internalArray;
....
private synchronized void writeObject(ObjectOutputStream stream) {
...
stream.write(internalArray);
...
}
}
黑客代碼
public class HackerObjectOutputStream extends ObjectOutputStream{
public void write (byte [] b) {
Modify b
}
}
...
YourClass yc = new YourClass();
...
HackerObjectOutputStream hoos = new HackerObjectOutputStream();
hoos.writeObject(yc);
• 字節流加密
保護虛擬機外的字節流的另一方式是對序列化包產生的流進行加密。字節流加密防止解碼或讀取被序列化的對象的私有狀態。如果決定加密,應該管理好密鑰,密鑰的存放地點以及將密鑰交付給反序列化程序的方式等。
• 需要提防的其他事宜
如果不可信任代碼無法創建對象,務必確保不可信任代碼也不能反序列化對象。切記對對象反序列化是創建對象的另一途徑。
比如說,如果一個applet創建了一個frame,在該frame上創建了警告標簽。如果該frame被另一應用程序序列化并被一個applet反序列化,務必使該frame出現時帶有同一個警告標簽。
原生方法應從以下幾個方面檢查原生方法:
• 它們返回什么
• 它們需要什么參數
• 它們是否繞過了安全檢查
• 它們是否是公共的,私有的等
• 它們是否包含能繞過包邊界的方法調用,從而繞過包保護
清除敏感信息當保存敏感信息時,如機密,盡量保存在如數組這樣的可變數據類型中,而不是保存在字符串這樣的不可變對象中,這樣使得敏感信息可以盡早顯式地被清除。不要指望Java平臺的自動垃圾回收來做這種清除,因為回收器可能不會清除這段內存,或者很久后才會回收。盡早清除信息使得來自虛擬機外部的堆檢查攻擊變得困難。
摘自:
http://www.matrix.org.cn/resource/article/2006-12-15/Java+Code+Security_199f1a70-8bf4-11db-ab77-2bbe780ebfbf.html
posted @
2006-12-29 20:47 xzc 閱讀(269) |
評論 (0) |
編輯 收藏
在oracle中sequence就是所謂的序列號,每次取的時候它會自動增加,一般用在需要按序列號排序的地方。
1、Create Sequence
你首先要有CREATE SEQUENCE或者CREATE ANY SEQUENCE權限,
CREATE SEQUENCE emp_sequence
INCREMENT BY 1 -- 每次加幾個
START WITH 1 -- 從1開始計數
NOMAXVALUE -- 不設置最大值
NOCYCLE -- 一直累加,不循環
CACHE 10;
一旦定義了emp_sequence,你就可以用CURRVAL,NEXTVAL
CURRVAL=返回 sequence的當前值
NEXTVAL=增加sequence的值,然后返回 sequence 值
比如:
emp_sequence.CURRVAL
emp_sequence.NEXTVAL
可以使用sequence的地方:
- 不包含子查詢、snapshot、VIEW的 SELECT 語句
- INSERT語句的子查詢中
- NSERT語句的VALUES中
- UPDATE 的 SET中
可以看如下例子:
INSERT INTO emp VALUES
(empseq.nextval, 'LEWIS', 'CLERK',7902, SYSDATE, 1200, NULL, 20);
SELECT empseq.currval FROM DUAL;
但是要注意的是:
- 第一次NEXTVAL返回的是初始值;隨后的NEXTVAL會自動增加你定義的INCREMENT BY值,然后返回增加后的值。CURRVAL 總是返回當前SEQUENCE的值,但是在第一次NEXTVAL初始化之后才能使用CURRVAL,否則會出錯。一次NEXTVAL會增加一次SEQUENCE的值,所以如果你在同一個語句里面使用多個NEXTVAL,其值就是不一樣的。明白?
- 如果指定CACHE值,ORACLE就可以預先在內存里面放置一些sequence,這樣存取的快些。cache里面的取完后,oracle自動再取一組到cache。 使用cache或許會跳號, 比如數據庫突然不正常down掉(shutdown abort),cache中的sequence就會丟失. 所以可以在create sequence的時候用nocache防止這種情況。
2、Alter Sequence
你或者是該sequence的owner,或者有ALTER ANY SEQUENCE 權限才能改動sequence. 可以alter除start至以外的所有sequence參數.如果想要改變start值,必須 drop sequence 再 re-create .
Alter sequence 的例子
ALTER SEQUENCE emp_sequence
INCREMENT BY 10
MAXVALUE 10000
CYCLE -- 到10000后從頭開始
NOCACHE ;
影響Sequence的初始化參數:
SEQUENCE_CACHE_ENTRIES =設置能同時被cache的sequence數目。
可以很簡單的Drop Sequence
DROP SEQUENCE order_seq;
-------------------------------------
drop sequence SEQ_GROUP_ID
-- Create sequence
create sequence SEQ_GROUP_ID
minvalue 1
maxvalue 9999999999
start with 1
increment by 1
cache 20;
select seq_group_id.nextval from dual
-------------------------------------
posted @
2006-12-28 11:01 xzc 閱讀(282) |
評論 (0) |
編輯 收藏
我每月到企業舉辦一小時的免費“理財講座”,一直都很受員工們的歡迎。講座內容很少涉及復雜難懂的技術操作層面,也幾乎不進入到產品介紹環節,因為據我了解,國內一般的中產白領們,目前普遍缺乏的是幾個重要的理財概念——這些概念,會影響他們以后的行為,假如他們能老老實實執行這些理財上的概念,至少堅持10年
以上,那么,每一個人都能成為百萬富翁。
第一個理財概念:
區分“投資”與“消費”
區分“投資”行為與“消費”行為。一般人消費前,沒有這種概念,學經濟學的人消費前會考慮,這個消費是屬于“投資”行為或是“消費”行為。
先請看一個明顯的例子:
10年前甲和乙是本科的同學,在社會工作5年后,不約而同積蓄了30萬元人民幣。5年前,他們都花掉了這30萬元。
甲去通州購買了一套房。
乙去買了一輛“奧迪”。
5年后的今天:
甲的房子,市值60萬元。
乙的二手車,市值只有5萬元。
兩人目前的資產,明顯有了很大差異,但他們的收入都一樣,而且同樣學歷、基本具備同樣的社會經驗,為何大家財富不一樣?
甲花錢買房是“投資”行為——錢其實沒有花出去,只是轉移在了房子里,以后還是都歸自己。
乙花錢買車是“消費”行為——錢是花出去的,給了別人,二手車用過10年后,幾乎一分不值。車跟房子不一樣,房子10年后,說不定已翻了好幾番。
再看第二個例子:
有一天,我的秘書向我提出一個問題:陳老師,我覺得客戶甲有點怪。她說:客戶甲去買一張演唱會的票,300元他嫌貴,猶豫很久,始終沒買,但客戶甲其實并不缺錢。但有一次,有一個著名企業總裁出版了一套“教導管理”光盤,6張光盤賣到天價1500元,客戶甲卻毫不猶豫將它買下來。為何¥300演唱票,客戶甲嫌貴,卻去買¥1500的幾張光盤呢?
解答如下:客戶甲是將學的經濟學的知識應用到日常生活里,客戶甲每花費錢的時候,會先想這花錢是‘投資’行為或是‘消費’行為?
買光盤,這1500元是“投資”行為,它其實沒有花出去,它增長了客戶甲的知識,讓客戶甲更有智慧,在未來的日子,客戶甲用新學的智慧,會賺回1500元的好幾倍,錢始終還在客戶甲的口袋。
但購買演唱會的票,是“消費”行為,是給了別人,再也拿不回來了。
在生活中,還有更多的日常例子:
(1) 客戶甲會花3萬人民幣去買一幅油畫,但不會花3萬去買二手車。
(2) 客戶甲會花1萬去買人壽保險,但不會花1萬去歐洲度假。
?。?) 客戶甲會很舍得花錢買書,但不舍得花錢去看電影。
以上哪些是“投資”行為,那些是“消費”行為,每個人都會有自己的判斷。下面是更多的例子,如果屬于“投資”行為,那么,多貴都不必討價還價,因為錢最終還是歸自己。
第二個理財概念:
“哈佛”教條
大家每個月都會將工資一部分儲蓄起來,有些人儲蓄10%工資,有些20%,有些30%。大部分人是一個月后,把沒有花出去的錢儲蓄起來,而且每個月儲蓄多少基本沒譜。
在著名的美國第一學府哈佛大學,第一堂的經濟學課,只教兩個概念。
第一個概念:花錢要區分“投資”行為或“消費”行為。
第二個概念:每月先儲蓄30%的工資,剩下來才進行消費。
哈佛教導出來的人,以后都很富有,并非主要因為他們是名校出身、收入豐厚,而是他們每月的行為,跟一般的普通老百姓,只有一點不一樣:
哈佛教條:儲蓄30%的工資是硬指標,剩下才消費。每月儲蓄的錢是每月最重要的目標,只會超額完成,剩下的錢就越來越多。
一般人:先花錢,能剩多少便儲蓄多少,儲蓄剩下的錢并不多。
第三個理財概念:
“理財三句話”
理財走不出三句話,如果每句話都能吃透,并且完全執行,那么,打工一族都可以變得非常富有。
很多朋友都知道客戶甲的出身——難民,一無所有。到加拿大學經濟學也是拿著獎學金,家里七兄弟姐妹,沒有錢送客戶甲們上大學,上大學后,從來沒問家里拿過錢。畢業后打工,但客戶甲堅持“理財三句話”原則,用經濟學學到的學問,用到日常生活里,一步步走下去。現在20年后,客戶甲有4套房,每月收租便有1萬多的收入,也算是半個富有的人。
其實每個人都做得到,在這公開這秘密。以前這些重要的理財概念,課程里面都有教。
再舉一些實例給大家看:巴菲特在他的書本里說他6歲開始儲蓄,每月30塊。到13歲時,當他有了3千塊,他買了一只股票。年年堅持儲蓄,年年堅持投資,十年如一日,他堅持了80年?,F在85歲,是美國首富,比“微軟”主席比爾·蓋茨還有錢。
學員有時候會問,如何能每年回報率達到10%以上。答:其實現在要銀行里面,它們提供很多理財產品:基金,外幣,QDII。 這些銀行產品略有一點風險,但風險假如你能有效的管理它,10%的回報率其實也不難。當然,假如沒有受過專業培訓,你自己是瞎摸,你會虧掉很多錢。但你有兩個途徑:
?。?) 花點錢去學。
(2)你自己沒時間,那么可以去找專業的理財師。
找專業理財師,要分辨他們的專業資格,你可以參考幾個條件:
(1) 已經考取了的理財規劃師認證:中國注冊理財規劃師(CFP),全名是Certified Financial Planner。2005年已經在北京舉行公開考試,現在很多銀行的從業人員都在考。合格率偏低,暫時銀行里面有資格的人也不多。
(2) 有10年以上的理財經驗。但其它有興趣想多認識理財學問的,可以參加公開課程,費用只是幾百元一節。參加學習的費用,是“投資”行為,并沒有“花出去”,以后還是歸你自己,學過以后,就不會“小錢精明,大錢糊涂”了。
一般人錯誤的理財觀念:
掙得多,所以富有
很多人認為,甲收入每月1.5萬元,乙收入每月8000元,甲便應該比乙富有,這觀念在社會上很普遍。但這是錯的觀念,錯得很離譜。錯在哪里?
富有的定義,并不是你每月工資掙得多,而是你每月“剩下多少”——剩下的才是財富。請看例子:
美國人每月工資高中國二、三倍,照一般的觀念看,一般的美國人應比中國人富有。但實際情況卻不是這樣。一般美國人都有幾張信用卡,他們喜歡消費,每月不單只是“月光一族”,更普遍是欠下信用卡不少的債。在美國,理財規劃師的理財講座,一般時間花在講“如何減少你的債務”。
一般美國人,銀行的儲蓄都不夠美金幾千元。在中國,沒有這種情況,中國人善于儲蓄,一般人在銀行都有存款,超過十幾萬元的,人數還不少。
所以,不要以為老美每月掙錢多就富有。其實,一般老美的白領比中國人的白領窮得多。當然,在北京見到的很多外派到北京工作的老美,是美國的精英,不是一般的美國白領,有錢人占多數。
中國的中層白領,比美國的白領富有。請記?。焊挥胁皇潜容^每月工資,而是比較“剩下儲蓄在銀行里的存款”,以這個定義來講,中國人中層白領在銀行的存款,遠比美國中層白領高。
還有一個例子:
一般人以為臺灣人工資平均高出內地一倍,他們自然比我們富有,這也是一個錯誤的觀念。
去過臺灣的朋友都知道,臺灣地鐵單程平均是12元,北京是3元;臺灣午飯平均要50元,北京平均15元;在臺灣租一套房6500元,北京在通州租一套房1500元。假如臺灣人每月掙15000元,減去房租6500元,交通費1000元,吃飯300元,交稅1500元,一點點娛樂2000元,“每月剩下1000元”。
北京的初級工程師,每月工資8000元,減去交稅1000元,減去房租1500元,交通費300元,吃飯1000元,娛樂1000元,“每月剩下3200元”。
請問:是臺灣人每月工資15000元,每月只剩下1000元的人富有,還是北京工程師,每月工資只有8000元,但每月剩下3200元的人富有呢?
中國經過20多年的改革,已經造就了富有的一批人,請看《財富》雜志一年前的“富有”的人的調查報告,他們調查手頭上持有“現金100萬美元存款的人”,在亞洲區有多少人擁有這種財富。
答案是:香港4萬人,臺灣8萬人,日本12萬,中國30萬。中國每年增長率遠遠超出其他亞洲國家。所以人們不會覺得奇怪,外資銀行到北京開業,老是在推廣“理財服務”,因為中國這個地方,正是比較欠缺這一塊的知識。
posted @
2006-12-16 13:09 xzc 閱讀(353) |
評論 (0) |
編輯 收藏