2009-08-03 9 views
8

मुझे फ़ाइल में डेटा डालना होगा क्योंकि मेरा अन्य फ़ंक्शन इनपुट के रूप में फ़ाइल लेता है।मैं एर्लांग में एक अस्थायी फ़ाइल नाम कैसे बना सकता हूं?

मैं एरलांग में एक अद्वितीय फ़ाइल नाम कैसे बना सकता हूं?

क्या यूनिक्स "tempfile" जैसी कुछ मौजूद है?

उत्तर

12

क्या आपका मतलब केवल अकुशल फ़ाइल नाम उत्पन्न करना है? उस स्थिति में सबसे सुरक्षित तरीका अब आप() और आपके कंप्यूटर के होस्टनाम के मिश्रण का उपयोग करना होगा (यदि आपके पास एक ही काम करने वाले कई नोड्स हैं)।

कुछ की तरह:

1> {A,B,C}=now(). 
{1249,304278,322000} 
2> N=node(). 
[email protected] 
3> lists:flatten(io_lib:format("~p-~p.~p.~p",[N,A,B,C])). 
"[email protected]" 
4> 
+4

चूंकि सभी को इसके बारे में पता नहीं है: erlang करने के लिए कॉल: अब() प्रत्येक बार अद्वितीय परिणाम वापस करने की गारंटी है। काफी उपयोगी संपत्ति ... – viraptor

+0

हाँ, बहुत उपयोगी है। एक और चीज है जो संदर्भ उत्पन्न करने के इस तरीके से बहुत उपयोगी है; आपको वहां पर नोडनाम मिलता है जो बहुत उपयोगी होता है यदि आप पहले यह सुनिश्चित करना चाहते हैं कि आईडी हमेशा अनूठी है (आप इसे स्थानीय संदर्भ के रूप में देख सकते हैं) और दूसरा यह जानने के लिए कि संदर्भ कहां से आता है। हमारे सिस्टम में (क्लस्टर और साझा डेटाटेबल्स आदि में एन नोड्स के साथ) हम केवल इस पहचानकर्ता (नोड + टाइम) का उपयोग करके नौकरी के बारे में हमें आवश्यक लॉग और जानकारी प्राप्त कर सकते हैं। –

+0

अगर ऐसी फ़ाइल पहले से मौजूद है तो यह असफल हो जाएगी। erlang: अब() गारंटी नहीं दे सकता कि फ़ाइल मौजूद नहीं है। –

9

तुम भी TMP = lib:nonl(os:cmd("mktemp")).

+2

थोड़ा उग्र, लेकिन 'स्ट्रिंग: स्ट्रिप (ओएस: सेमीडी ("mktemp"), दाएं, $ \ n)' उस कष्टप्रद अदृश्य न्यूलाइन से बच सकते हैं जो आमतौर पर अंत में वापस आ जाएगा। – zxq9

+1

छोटा संस्करण: 'lib: nonl (os: cmd (" mktemp "))'। –

+0

हालांकि यह काम करता है, यह मंच निर्भर है। –

6

उपयोग कर सकते हैं या आप एक त्वरित और आसान अद्वितीय indentifier के लिए

erlang:phash2(make_ref())

कर सकता है। 2^82 कॉल तक अद्वितीय जो आपके लिए पर्याप्त होना चाहिए। मुझे उपयोग के लिए नोड नाम के साथ एक टाइमस्टैम्प स्वरूपण करने से यह आसान लगता है।

1

देर जवाब: मैं बस test_server मॉड्यूल जो खरोंच निर्देशिका समर्थन हासिल है, एक नज़र लायक

http://www.erlang.org/doc/man/test_server.html#temp_name-1

+0

यह गारंटी नहीं देता है कि यह फ़ाइल उस समय मौजूद नहीं होगी जब आप इस फ़ाइल को बनाने का प्रयास करेंगे। तो यह सुरक्षित नहीं है। यही कारण है कि 'stdlib.h' में 'mkstemp' है। जीएनयू कोरुटल्स से 'mktemp' आंतरिक रूप से' mkstemp 'कॉल का उपयोग करता है। –

0

मैं अंत में इस समस्या को मिला है देखा - और मेरे उपयोगकर्ता विंडोज का एक मिश्रण का उपयोग कर रहा है और लिनक्स सिस्टम, इसलिए पुरानी कोशिश की और सत्य lib:nonl(os:cmd("mktemp")) विधि अब इसे काटने वाला नहीं है।

तो यहां यह है कि मैंने mktemp/1 फ़ंक्शन के साथ दोनों से संपर्क किया है, जो एक फ़ाइल नाम लौटाता है और mktemp_dir/1 फ़ंक्शन जो एक निर्देशिका देता है (इसे बनाने के बाद)।

-spec mktemp(Prefix) -> Result 
    when Prefix :: string(), 
     Result :: {ok, TempFile :: file:filename()} 
        | {error, Reason :: file:posix()}. 

mktemp(Prefix) -> 
    Rand = integer_to_list(binary:decode_unsigned(crypto:strong_rand_bytes(8)), 36), 
    TempPath = filename:basedir(user_cache, Prefix), 
    TempFile = filename:join(TempPath, Rand), 
    Result1 = file:ensure_dir(TempFile), 
    Result2 = file:write_file(TempFile, <<>>), 
    case {Result1, Result2} of 
     {ok, ok} -> {ok, TempFile}; 
     {ok, Error} -> Error; 
     {Error, _} -> Error 
    end. 

और निर्देशिका संस्करण:

-spec mktemp_dir(Prefix) -> Result 
    when Prefix :: string(), 
     Result :: {ok, TempDir :: file:filename()} 
       | {error, Reason :: file:posix()}. 

mktemp_dir(Prefix) -> 
    Rand = integer_to_list(binary:decode_unsigned(crypto:strong_rand_bytes(8)), 36), 
    TempPath = filename:basedir(user_cache, Prefix), 
    TempDir = filename:join(TempPath, Rand), 
    Result1 = file:ensure_dir(TempDir), 
    Result2 = file:make_dir(TempDir), 
    case {Result1, Result2} of 
     {ok, ok} -> {ok, TempDir}; 
     {ok, Error} -> Error; 
     {Error, _} -> Error 
    end. 

इन दोनों मूल रूप से एक ही बात करते हैं: हम, एक बाइनरी के रूप में दृढ़ता से यादृच्छिक नाम एक base36 स्ट्रिंग के लिए कि कनवर्ट करते हैं, और जो कुछ भी करने के लिए संलग्न ओएस हमें एक सुरक्षित उपयोगकर्ता-स्थानीय अस्थायी कैश स्थान के रूप में लौटाता है।

एक यूनिक्स प्रकार प्रणाली पर, हम केवल filename:join(["/tmp", Prefix, Rand]) का उपयोग कर सकते हैं लेकिन विंडोज़ पर /tmp की अनुपलब्धता यहां पूरे बिंदु की तरह है।