xmerl_scan.erl

来自「OTP是开放电信平台的简称」· ERL 代码 · 共 438 行 · 第 1/2 页

ERL
438
字号
%%% @spec cont_state(ContinuationState, S::global_state()) -> global_state()%%% @doc For controlling the ContinuationState, to be used in a continuation%%% function, and called when the parser encounters the end of the byte stream.%%% See <a href="xmerl_examples.html">tutorial</a> on customization functions.cont_state(X, S=#xmerl_scanner{fun_states = FS}) ->    FS1 = FS#xmerl_fun_states{cont = X},    S#xmerl_scanner{fun_states = FS1}.%% @spec file(Filename::string()) -> {xmlElement(),Rest}%%   Rest = list()%% @equiv file(Filename, [])file(F) ->    file(F, []).%% @spec file(Filename::string(), Options::option_list()) -> {xmlElement(),Rest}%%   Rest = list()%%% @doc Parse file containing an XML documentfile(F, Options) ->    ExtCharset=case lists:keysearch(encoding,1,Options) of		   {value,{_,Val}} -> Val;		   false -> undefined	       end,    case int_file(F,Options,ExtCharset) of	{Res, Tail,S=#xmerl_scanner{close_fun=Close}} ->	    Close(S), % for side effects only - final state is dropped	    {Res,Tail};	{error, Reason} ->	    {error, Reason}    end.int_file(F, Options,_ExtCharset) ->     %%io:format("int_file F=~p~n",[F]),    case file:read_file(F) of	{ok, Bin} ->	    int_string(binary_to_list(Bin), Options, filename:dirname(F),F);	Error ->	    Error    end.int_file_decl(F, Options,_ExtCharset) ->%     io:format("int_file_decl F=~p~n",[F]),    case file:read_file(F) of	{ok, Bin} ->	    int_string_decl(binary_to_list(Bin), Options, filename:dirname(F),F);	Error ->	    Error    end.%% @spec string(Text::list()) -> {xmlElement(),Rest}%%   Rest = list()%% @equiv string(Test, [])string(Str) ->      string(Str, []).%% @spec string(Text::list(),Options::option_list()) -> {xmlElement(),Rest}%%   Rest = list()%%% @doc Parse string containing an XML documentstring(Str, Options) ->     {Res, Tail, S=#xmerl_scanner{close_fun = Close}} =	int_string(Str, Options,file_name_unknown),    Close(S),    % for side effects only - final state is dropped    {Res,Tail}.int_string(Str, Options,FileName) ->    {ok,  XMLBase} = file:get_cwd(),    int_string(Str, Options, XMLBase, FileName).int_string(Str, Options, XMLBase, FileName) ->    S0=initial_state0(Options,XMLBase),    S = S0#xmerl_scanner{filename=FileName},    %%io:format("int_string1, calling xmerl_lib:detect_charset~n",[]),    %% In case of no encoding attribute in document utf-8 is default, but    %% another character set may be detected with help of Byte Order Marker or    %% with help of the encoding of the first 4 bytes.    case xmerl_lib:detect_charset(S#xmerl_scanner.encoding,Str) of	{auto,'iso-10646-utf-1',Str2} ->	    scan_document(Str2, S#xmerl_scanner{encoding="iso-10646-utf-1"});	{external,'iso-10646-utf-1',Str2} ->	    scan_document(Str2, S#xmerl_scanner{encoding="iso-10646-utf-1"});	{undefined,undefined,Str2} -> %% no auto detection	    scan_document(Str2, S);	{external,ExtCharset,Str2} -> 	    %% no auto detection, ExtCharset is an explicitly provided	    %% 7 bit,8 bit or utf-8 encoding	    scan_document(Str2, S#xmerl_scanner{encoding=atom_to_list(ExtCharset)})    end.int_string_decl(Str, Options, XMLBase, FileName) ->    S0=initial_state0(Options,XMLBase),    S = S0#xmerl_scanner{filename=FileName},    case xmerl_lib:detect_charset(S#xmerl_scanner.encoding,Str) of	{auto,'iso-10646-utf-1',Str2} ->	    scan_decl(Str2, S#xmerl_scanner{encoding="iso-10646-utf-1"});	{external,'iso-10646-utf-1',Str2} ->	    scan_decl(Str2, S#xmerl_scanner{encoding="iso-10646-utf-1"});	{undefined,undefined,Str2} ->	    scan_decl(Str2, S);	{external,ExtCharset,Str2} ->	    scan_decl(Str2, S#xmerl_scanner{encoding=atom_to_list(ExtCharset)})    end.    initial_state0(Options,XMLBase) ->    initial_state(Options, #xmerl_scanner{		    event_fun = fun event/2,		    hook_fun = fun hook/2,		    acc_fun = fun acc/3,		    fetch_fun = fun fetch/2,		    close_fun = fun close/1,		    continuation_fun = fun cont/3,		    rules_read_fun = fun rules_read/3,		    rules_write_fun = fun rules_write/4,		    rules_delete_fun= fun rules_delete/3,		    xmlbase = XMLBase		   }).initial_state([{event_fun, F}|T], S) ->    initial_state(T, S#xmerl_scanner{event_fun = F});initial_state([{event_fun, F, ES}|T], S) ->    S1 = event_state(ES, S#xmerl_scanner{event_fun = F}),    initial_state(T, S1);initial_state([{acc_fun, F}|T], S) ->    initial_state(T, S#xmerl_scanner{acc_fun = F});initial_state([{hook_fun, F}|T], S) ->    initial_state(T, S#xmerl_scanner{hook_fun = F});initial_state([{hook_fun, F, HS}|T], S) ->    S1 = hook_state(HS, S#xmerl_scanner{hook_fun = F}),    initial_state(T, S1);initial_state([{close_fun, F}|T], S) ->    initial_state(T, S#xmerl_scanner{close_fun = F});initial_state([{fetch_fun, F}|T], S) ->    initial_state(T, S#xmerl_scanner{fetch_fun = F});initial_state([{fetch_fun, F, FS}|T], S) ->    S1 = fetch_state(FS, S#xmerl_scanner{fetch_fun = F}),    initial_state(T, S1);initial_state([{fetch_path, P}|T], S) ->    initial_state(T, S#xmerl_scanner{fetch_path = P});initial_state([{continuation_fun, F}|T], S) ->    initial_state(T, S#xmerl_scanner{continuation_fun = F});initial_state([{continuation_fun, F, CS}|T], S) ->    S1 = cont_state(CS, S#xmerl_scanner{continuation_fun = F}),    initial_state(T, S1);initial_state([{rules, R}|T], S) ->    initial_state(T, S#xmerl_scanner{rules = R,				     keep_rules = true});initial_state([{rules, Read, Write, RS}|T], S) ->    S1 = rules_state(RS, S#xmerl_scanner{rules_read_fun = Read,					 rules_write_fun = Write,					 keep_rules = true}),    initial_state(T, S1);initial_state([{user_state, F}|T], S) ->    initial_state(T, S#xmerl_scanner{user_state = F});initial_state([{space, L}|T], S) ->    initial_state(T, S#xmerl_scanner{space = L});initial_state([{line, L}|T], S) ->    initial_state(T, S#xmerl_scanner{line = L});initial_state([{namespace_conformant, F}|T], S) when F==true; F==false ->    initial_state(T, S#xmerl_scanner{namespace_conformant = F});initial_state([{validation, F}|T], S)   when F==off; F==dtd; F==schema; F==true; F==false ->    initial_state(T, S#xmerl_scanner{validation = validation_value(F)});initial_state([{schemaLocation, SL}|T], S) when is_list(SL) ->    initial_state(T, S#xmerl_scanner{schemaLocation=SL});initial_state([{quiet, F}|T], S) when F==true; F==false ->    initial_state(T, S#xmerl_scanner{quiet = F});initial_state([{doctype_DTD,DTD}|T], S) ->    initial_state(T,S#xmerl_scanner{doctype_DTD = DTD});initial_state([{text_decl,Bool}|T], S) ->    initial_state(T,S#xmerl_scanner{text_decl=Bool});initial_state([{environment,Env}|T], S) ->    initial_state(T,S#xmerl_scanner{environment=Env});initial_state([{xmlbase, D}|T], S) ->    initial_state(T, S#xmerl_scanner{xmlbase = D});initial_state([{encoding, Enc}|T], S) ->    initial_state(T, S#xmerl_scanner{encoding = Enc});initial_state([], S=#xmerl_scanner{rules = undefined}) ->    Tab = ets:new(rules, [set, public]),    S#xmerl_scanner{rules = Tab};initial_state([], S) ->    S.validation_value(true) ->    dtd;validation_value(false) ->    off;validation_value(F) ->    F.%%% -----------------------------------------------------%%% Default modifier functions%%% Hooks:%%% - {element, Line, Name, Attrs, Content}%%% - {processing_instruction, Line, Data}hook(X, State) ->    {X, State}.%%% Events:%%%%%% #xmerl_event{event : started | ended,%%%              line  : integer(),%%%		 col   : integer(),%%%              data}%%%%%% Data		Events%%% document		started, ended%%% #xmlElement		started, ended%%% #xmlAttribute	ended%%% #xmlPI		ended%%% #xmlComment		ended%%% #xmlText		endedevent(_X, S) ->    S.%% The acc/3 function can return either {Acc

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?