আমার কোডটি একটি জেআর ফাইলের মধ্যে চলে, foo.jar বলুন এবং কোডটিতে আমার foo.jar চলমান ফোল্ডারে জানতে হবে।
সুতরাং, যদি foo.jar থাকে তবে C:\FOO\
আমি আমার বর্তমান কার্যনির্বাহী ডিরেক্টরিটি নির্বিশেষে সেই পথটি পেতে চাই।
আমার কোডটি একটি জেআর ফাইলের মধ্যে চলে, foo.jar বলুন এবং কোডটিতে আমার foo.jar চলমান ফোল্ডারে জানতে হবে।
সুতরাং, যদি foo.jar থাকে তবে C:\FOO\
আমি আমার বর্তমান কার্যনির্বাহী ডিরেক্টরিটি নির্বিশেষে সেই পথটি পেতে চাই।
উত্তর:
return new File(MyClass.class.getProtectionDomain().getCodeSource().getLocation()
.toURI()).getPath();
আপনার ক্লাসের নাম দিয়ে "মাই ক্লাস" প্রতিস্থাপন করুন।
স্পষ্টতই, আপনার ক্লাসটি কোনও ফাইলবিহীন অবস্থান থেকে লোড করা হলে এটি অদ্ভুত কাজ করবে।
toURI()
ধাপ স্পেস এবং pluses সহ বিশেষ অক্ষর, সঙ্গে এড়ানোর সমস্যা অত্যাবশ্যক। সঠিক ওয়ান-লাইনারটি হ'ল: return new File(MyClass.class.getProtectionDomain().getCodeSource().getLocation().toURI());
ব্যবহার URLDecoder
অনেকগুলি বিশেষ চরিত্রের জন্য কাজ করে না। আরও তথ্যের জন্য নীচে আমার উত্তর দেখুন।
getProtectionDomain
যদি আপনি স্ট্র্যাকট্র্যাস থেকে আপনার ক্লাসটি পান তবে তা বাতিল:val strace = Thread.currentThread().getStackTrace; val path = strace(1).getClass.getProtectionDomain
আমার জন্য সেরা সমাধান:
String path = Test.class.getProtectionDomain().getCodeSource().getLocation().getPath();
String decodedPath = URLDecoder.decode(path, "UTF-8");
এটি স্পেস এবং বিশেষ অক্ষরগুলির সাথে সমস্যার সমাধান করা উচিত।
URLDecoder.decode(ClassLoader.getSystemClassLoader().getResource(".").getPath(), "UTF-8");
লিনাক্সে @ আইভিগজিয়ানির সাথে ( ) মিশ্রণে নিখুঁত সমাধান বলে মনে হচ্ছে । তবে আমি উইন্ডোজটিতে চেষ্টা করিনি try
URLDecoder
বিশেষ অক্ষরগুলি ডিকোড করতে ব্যবহার করার পরামর্শ দেওয়া হয় না । বিশেষত, এর মতো অক্ষরগুলি +
ভুলভাবে স্পেসে ডিকোড করা হবে। বিস্তারিত জানার জন্য আমার উত্তর দেখুন।
প্রাপ্ত File
একটি প্রদত্ত জন্য Class
, দুই ধাপ আছে:
Class
একটি থেকেURL
URL
একটি থেকেFile
উভয় পদক্ষেপ বোঝা গুরুত্বপূর্ণ, এবং সেগুলি সংঘাতের নয় not
আপনার কাছে একবার File
, আপনি কল করতে পারেনgetParentFile
যদি প্রয়োজন হয় তবে এটি ধারণকৃত ফোল্ডারটি করতে পারেন।
Class
থেকেURL
অন্যান্য উত্তরে যেমন আলোচনা করা হয়েছে, তে URL
প্রাসঙ্গিক হওয়ার দুটি উপায় রয়েছে Class
।
URL url = Bar.class.getProtectionDomain().getCodeSource().getLocation();
URL url = Bar.class.getResource(Bar.class.getSimpleName() + ".class");
উভয় আগপাছ আছে।
getProtectionDomain
পদ্ধতির শ্রেণী (যেমন, ধারণকারী JAR- র ফাইল) বেস অবস্থান উৎপাদ। তবে, জাভা রানটাইমের সুরক্ষা নীতি SecurityException
কল করার সময় নিক্ষেপ করবেgetProtectionDomain()
, তাই যদি আপনার অ্যাপ্লিকেশনটি বিভিন্ন পরিবেশে চালিত হওয়ার প্রয়োজন হয় পরীক্ষা করা ভাল।
getResource
পদ্ধতির বর্গ, যেখান থেকে আপনি অতিরিক্ত স্ট্রিং ম্যানিপুলেশন সঞ্চালন করতে হবে সম্পূর্ণ URL সম্পদ পথ উৎপাদ। এটি একটি file:
পাথ হতে পারে তবে এটি কোনও OSGi কাঠামোর মধ্যে কার্যকর করার সময় jar:file:
বা কিছুটা nastier ও হতে পারে bundleresource://346.fwk2106232034:4/foo/Bar.class
। বিপরীতভাবে, getProtectionDomain
পদ্ধতির সঠিকভাবে ফলন করে afile:
এমনকি ওএসজিআইয়ের মধ্যে থেকে ইউআরএল ।
নোট করুন getResource("")
এবং উভয়ই getResource(".")
আমার পরীক্ষায় ব্যর্থ হয়েছে, যখন ক্লাসটি একটি জেআর ফাইলের মধ্যে অবস্থান করেছিল; উভয় আহ্বান বাতিল। সুতরাং আমি এটি পরিবর্তে উপরে প্রদর্শিত # 2 অনুরোধের পরামর্শ দিচ্ছি, কারণ এটি নিরাপদ বলে মনে হচ্ছে।
URL
থেকেFile
যে কোনও উপায়ে, একবার আপনার সাথে থাকলে URL
, পরবর্তী পদক্ষেপটি একটিতে রূপান্তরিত হয় File
। এটি তার নিজস্ব চ্যালেঞ্জ; দেখতে এটি সম্পর্কে Kohsuke Kawaguchi এর ব্লগ পোস্টে সম্পূর্ণ বিবরণের জন্য, কিন্তু সংক্ষেপে, আপনি ব্যবহার করতে পারেনnew File(url.toURI())
যতদিন URL টি সম্পূর্ণরূপে সুগঠিত হয়।
সবশেষে, আমি ব্যবহার করে অত্যন্ত নিরুৎসাহিত করবURLDecoder
। URL- এ কিছু অক্ষর :
এবং /
বিশেষ করে, কার্যকর URL এনকোডেড অক্ষর নয়। URL ডিকোডার জাভাদোক থেকে :
অনুমান করা হয় যে এনকোডযুক্ত স্ট্রিংয়ের সমস্ত অক্ষর নিম্নলিখিতগুলির মধ্যে একটি: "ক" মাধ্যমে "জেড", "এ" "জেড" এর মাধ্যমে, "0" "9" এর মাধ্যমে এবং "-", "_", " .", এবং "*". "%" অক্ষরটি অনুমোদিত তবে একটি বিশেষ পালানো ক্রমের সূচনা হিসাবে ব্যাখ্যা করা হয়।
...
দুটি সম্ভাব্য উপায় রয়েছে যাতে এই ডিকোডারটি অবৈধ স্ট্রিংয়ের সাথে মোকাবিলা করতে পারে। এটি হয় অবৈধ চরিত্রকে একা ফেলে যেতে পারে অথবা এটি একটি অবৈধআর্গুমেন্টএক্সসেপশন ফেলে দিতে পারে। ডিকোডারটি কোন পদ্ধতির গ্রহণ করে তা বাস্তবায়নের বাকি রয়েছে।
অনুশীলনে, URLDecoder
সাধারণত IllegalArgumentException
উপরে হুমকি হিসাবে ছুঁড়ে না । এবং যদি আপনার ফাইলপথটিতে শূন্যস্থানগুলি এনকোড করা থাকে তবে %20
এই পদ্ধতির কাজ হতে পারে। তবে, যদি আপনার ফাইলপথের অন্যান্য অ-অক্ষরযুক্ত অক্ষর থাকে তবে আপনার ফাইলের পাথটি ম্যাংলিংয়ের ক্ষেত্রে +
আপনার সমস্যা হবে URLDecoder
।
এই পদক্ষেপগুলি অর্জন করতে আপনার নীচের মতো পদ্ধতি থাকতে পারে:
/**
* Gets the base location of the given class.
* <p>
* If the class is directly on the file system (e.g.,
* "/path/to/my/package/MyClass.class") then it will return the base directory
* (e.g., "file:/path/to").
* </p>
* <p>
* If the class is within a JAR file (e.g.,
* "/path/to/my-jar.jar!/my/package/MyClass.class") then it will return the
* path to the JAR (e.g., "file:/path/to/my-jar.jar").
* </p>
*
* @param c The class whose location is desired.
* @see FileUtils#urlToFile(URL) to convert the result to a {@link File}.
*/
public static URL getLocation(final Class<?> c) {
if (c == null) return null; // could not load the class
// try the easy way first
try {
final URL codeSourceLocation =
c.getProtectionDomain().getCodeSource().getLocation();
if (codeSourceLocation != null) return codeSourceLocation;
}
catch (final SecurityException e) {
// NB: Cannot access protection domain.
}
catch (final NullPointerException e) {
// NB: Protection domain or code source is null.
}
// NB: The easy way failed, so we try the hard way. We ask for the class
// itself as a resource, then strip the class's path from the URL string,
// leaving the base path.
// get the class's raw resource path
final URL classResource = c.getResource(c.getSimpleName() + ".class");
if (classResource == null) return null; // cannot find class resource
final String url = classResource.toString();
final String suffix = c.getCanonicalName().replace('.', '/') + ".class";
if (!url.endsWith(suffix)) return null; // weird URL
// strip the class's path from the URL string
final String base = url.substring(0, url.length() - suffix.length());
String path = base;
// remove the "jar:" prefix and "!/" suffix, if present
if (path.startsWith("jar:")) path = path.substring(4, path.length() - 2);
try {
return new URL(path);
}
catch (final MalformedURLException e) {
e.printStackTrace();
return null;
}
}
/**
* Converts the given {@link URL} to its corresponding {@link File}.
* <p>
* This method is similar to calling {@code new File(url.toURI())} except that
* it also handles "jar:file:" URLs, returning the path to the JAR file.
* </p>
*
* @param url The URL to convert.
* @return A file path suitable for use with e.g. {@link FileInputStream}
* @throws IllegalArgumentException if the URL does not correspond to a file.
*/
public static File urlToFile(final URL url) {
return url == null ? null : urlToFile(url.toString());
}
/**
* Converts the given URL string to its corresponding {@link File}.
*
* @param url The URL to convert.
* @return A file path suitable for use with e.g. {@link FileInputStream}
* @throws IllegalArgumentException if the URL does not correspond to a file.
*/
public static File urlToFile(final String url) {
String path = url;
if (path.startsWith("jar:")) {
// remove "jar:" prefix and "!/" suffix
final int index = path.indexOf("!/");
path = path.substring(4, index);
}
try {
if (PlatformUtils.isWindows() && path.matches("file:[A-Za-z]:.*")) {
path = "file:/" + path.substring(5);
}
return new File(new URL(path).toURI());
}
catch (final MalformedURLException e) {
// NB: URL is not completely well-formed.
}
catch (final URISyntaxException e) {
// NB: URL is not completely well-formed.
}
if (path.startsWith("file:")) {
// pass through the URL as-is, minus "file:" prefix
path = path.substring(5);
return new File(path);
}
throw new IllegalArgumentException("Invalid URL: " + url);
}
আপনি এই পদ্ধতিগুলি সায়জভা কমন লাইব্রেরিতে খুঁজে পেতে পারেন :
আপনি এটি ব্যবহার করতে পারেন:
CodeSource codeSource = YourMainClass.class.getProtectionDomain().getCodeSource();
File jarFile = new File(codeSource.getLocation().toURI().getPath());
String jarDir = jarFile.getParentFile().getPath();
আপনার বর্তমান শ্রেণীর জন্য URL খুঁজে পেতে ClassLoader.getResource () ব্যবহার করুন।
উদাহরণ স্বরূপ:
package foo;
public class Test
{
public static void main(String[] args)
{
ClassLoader loader = Test.class.getClassLoader();
System.out.println(loader.getResource("foo/Test.class"));
}
}
( একই উদাহরণ থেকে নেওয়া এই উদাহরণ ।)
ডিরেক্টরিটি সন্ধান করার জন্য আপনাকে ম্যানুয়ালি ইউআরএল আলাদা করতে হবে। একটি জার ইউআরএলের ফর্ম্যাটের জন্য জারক্লাসলৌডার টিউটোরিয়ালটি দেখুন ।
NPE
আপনি যে প্রশ্নটি জিজ্ঞাসা করেছিলেন তার উত্তর না দেওয়ার কারণ হবেনা (জেআর দিরের দিকে জিজ্ঞাসা করা হয়েছিল এবং আপনি একেবারে পৃথক প্রশ্নের উত্তর দিয়েছেন: শ্রেণীর পথে)। ২. অন্যদের দ্বারা নির্দেশিত হিসাবে, এবং আমি একই সমস্যা পেয়েছি, এটি অ্যাপলেটগুলির জন্য কাজ করে না। 3. ফিরে পথ এ সব ক্যানোনিকাল পথ প্রতিনিধিত্বের নয়: jar:file:/listener/build/libs/listener-1.0.0-all.jar!/shared/Test.class
।
আমি অবাক হয়ে দেখেছি যে কেউই সম্প্রতি ব্যবহারের প্রস্তাব করেনি Path
। এখানে একটি তলব রয়েছে: " বর্গ বিভিন্ন পদ্ধতি পথ সম্পর্কে তথ্য প্রাপ্ত করতে ব্যবহৃত করা যেতে পারে, পথের এক্সেস উপাদান অন্তর্ভুক্ত, অন্যান্য ধরনের, অথবা একটি পথের সার অংশ পাথ রূপান্তর "Path
সুতরাং, একটি ভাল বিকল্প হ'ল Path
আপত্তিজনক হিসাবে পাওয়া:
Path path = Paths.get(Test.class.getProtectionDomain().getCodeSource().getLocation().toURI());
লিনাক্স, ম্যাক এবং উইন্ডোজে আমার জন্য একমাত্র সমাধান:
public static String getJarContainingFolder(Class aclass) throws Exception {
CodeSource codeSource = aclass.getProtectionDomain().getCodeSource();
File jarFile;
if (codeSource.getLocation() != null) {
jarFile = new File(codeSource.getLocation().toURI());
}
else {
String path = aclass.getResource(aclass.getSimpleName() + ".class").getPath();
String jarFilePath = path.substring(path.indexOf(":") + 1, path.indexOf("!"));
jarFilePath = URLDecoder.decode(jarFilePath, "UTF-8");
jarFile = new File(jarFilePath);
}
return jarFile.getParentFile().getAbsolutePath();
}
আমার একই সমস্যা ছিল এবং আমি এটি সেভাবে সমাধান করেছি:
File currentJavaJarFile = new File(Main.class.getProtectionDomain().getCodeSource().getLocation().getPath());
String currentJavaJarFilePath = currentJavaJarFile.getAbsolutePath();
String currentRootDirectoryPath = currentJavaJarFilePath.replace(currentJavaJarFile.getName(), "");
আমি আশা করি আমি আপনার জন্য সহায়ক ছিলাম।
এখানে অন্যান্য মন্তব্যে আপগ্রেড করা হয়েছে, যা সুনির্দিষ্টতার জন্য আমার কাছে অসম্পূর্ণ বলে মনে হচ্ছে
.jar ফাইলের বাইরে একটি আপেক্ষিক "ফোল্ডার" ব্যবহার করে (জারের একই জায়গায়):
String path =
YourMainClassName.class.getProtectionDomain().
getCodeSource().getLocation().getPath();
path =
URLDecoder.decode(
path,
"UTF-8");
BufferedImage img =
ImageIO.read(
new File((
new File(path).getParentFile().getPath()) +
File.separator +
"folder" +
File.separator +
"yourfile.jpg"));
URLDecoder
বিশেষ অক্ষরগুলি ডিকোড করতে ব্যবহার করার পরামর্শ দেওয়া হয় না । বিশেষত, এর মতো অক্ষরগুলি +
ভুলভাবে স্পেসে ডিকোড করা হবে। বিস্তারিত জানার জন্য আমার উত্তর দেখুন।
URLDecoder
এর নাম সত্ত্বেও, ইউআরএল ডিকোড করার জন্য এবং প্যারামিটারের নাম এবং মানগুলি তৈরি করে, ইউআরএল নয়।
জার ফাইলটি চালনার পথ পাওয়ার জন্য আমি উপরের সমাধানগুলি অধ্যয়ন করেছি এবং সমস্ত পদ্ধতির চেষ্টা করেছি যা একে অপরের মধ্যে কিছু পার্থক্য রয়েছে। যদি এই কোডগুলি Eclipse IDE এ চলমান থাকে তবে তাদের সকলকেই নির্দেশিত বর্গ সহ ফাইলটির সন্ধান করতে এবং সন্ধানের পথটি সহ একটি সূচিত ফাইলটি খুলতে বা তৈরি করতে সক্ষম হওয়া উচিত।
তবে এটি মুশকিল, যখন চালানোযোগ্য জার ফাইলটি সরাসরি বা কমান্ড লাইনের মাধ্যমে চালানো হয়, এটি ব্যর্থ হবে কারণ উপরের পদ্ধতিগুলি থেকে জার ফাইলের পথটি জার ফাইলটিতে একটি অভ্যন্তরীণ পথ দেবে, এ কারণেই এটি সর্বদা একটি পথ দেয় যেমন
আরএসসিআর: প্রকল্পের নাম (সম্ভবত আমার বলা উচিত এটি মূল শ্রেণীর ফাইলের প্যাকেজের নাম - নির্দেশিত শ্রেণি)
আমি আরএসসিআর: ... একটি বাহ্যিক পাথে পাথ রূপান্তর করতে পারি না, এটি যখন গ্রহ আইডির বাইরে জার ফাইলটি চালানো হয় তখন এটি জার ফাইলটির পাথ পায় না।
Eclipse IDE এর বাইরে জার ফাইল চালানোর পথ পাওয়ার একমাত্র সম্ভাব্য উপায়
System.getProperty("java.class.path")
এই কোড লাইনটি চলমান জার ফাইলের জীবন্ত পথ (ফাইলের নাম সহ) ফিরিয়ে দিতে পারে (নোট করুন যে ফেরতের পথটি কার্যনির্বাহী ডিরেক্টরি নয়), জাভা নথি এবং কিছু লোক বলেছে যে এটি সমস্ত শ্রেণীর ফাইলের পথগুলি ফিরিয়ে দেবে একই ডিরেক্টরিতে, তবে আমার পরীক্ষাগুলি হিসাবে যদি একই ডিরেক্টরিতে অনেকগুলি জার ফাইল অন্তর্ভুক্ত থাকে তবে এটি কেবল চলমান জারের পথটি ফেরত দেয় (একাধিক পাথ ইস্যু সম্পর্কে যা বাস্তবে এটি গ্রহনে ঘটেছিল)।
java.class.path
মাল্টিভ্যালু করা যেতে পারে। সেই মানগুলির মধ্যে একটি অবশ্যই ডিরেক্টরি বা জার ফাইল সরবরাহ করবে যেখানে বর্তমান বর্গটি অবস্থিত তবে কোনটি?
অন্যান্য উত্তরগুলি কোড উত্সকে নির্দেশ করে বলে মনে হচ্ছে যা জার ফাইলের অবস্থান যা কোনও ডিরেক্টরি নয়।
ব্যবহার
return new File(MyClass.class.getProtectionDomain().getCodeSource().getLocation().toURI().getPath()).getParentFile();
উপরের নির্বাচিত উত্তরটি কাজ করছে না যদি আপনি জারোমে ডেস্কটপ এনভায়রনমেন্ট (কোনও স্ক্রিপ্ট বা টার্মিনাল থেকে নয়) থেকে তার জারটি ক্লিক করে চালান।
পরিবর্তে, আমি পছন্দ করি যে নীচের সমাধানটি সর্বত্র কাজ করছে:
try {
return URLDecoder.decode(ClassLoader.getSystemClassLoader().getResource(".").getPath(), "UTF-8");
} catch (UnsupportedEncodingException e) {
return "";
}
URLDecoder
বিশেষ অক্ষরগুলি ডিকোড করতে ব্যবহার করার পরামর্শ দেওয়া হয় না । বিশেষত, এর মতো অক্ষরগুলি +
ভুলভাবে স্পেসে ডিকোড করা হবে। বিস্তারিত জানার জন্য আমার উত্তর দেখুন।
NullPointerException
NPE
যদি বয়াম মধ্যে কোন সম্পদ।
প্রকৃতপক্ষে এখানে একটি আরও ভাল সংস্করণ - কোনও ফোল্ডারের নামের মধ্যে যদি জায়গা থাকে তবে পুরানোটি ব্যর্থ হয়েছিল।
private String getJarFolder() {
// get name and path
String name = getClass().getName().replace('.', '/');
name = getClass().getResource("/" + name + ".class").toString();
// remove junk
name = name.substring(0, name.indexOf(".jar"));
name = name.substring(name.lastIndexOf(':')-1, name.lastIndexOf('/')+1).replace('%', ' ');
// remove escape characters
String s = "";
for (int k=0; k<name.length(); k++) {
s += name.charAt(k);
if (name.charAt(k) == ' ') k += 2;
}
// replace '/' with system separator char
return s.replace('/', File.separatorChar);
}
অ্যাপলেটগুলির ব্যর্থতা হিসাবে, আপনার সাধারণত স্থানীয় ফাইলগুলিতে যাইহোক অ্যাক্সেস থাকবে না। আমি জেডাব্লুএস সম্পর্কে খুব বেশি জানি না তবে স্থানীয় ফাইলগুলি পরিচালনা করতে অ্যাপ্লিকেশনটি ডাউনলোড করা সম্ভব নাও হতে পারে??
আমি জার চালানোর পথটি ব্যবহার করার চেষ্টা করেছি
String folder = MyClassName.class.getProtectionDomain().getCodeSource().getLocation().getPath();
সি: \ অ্যাপ> জাভা-অ্যাপ্লিকেশন.জার
বয়াম ফোল্ডারে "application.jar" নামের অ্যাপ্লিকেশন, Windows এ চালনা " C: \ অ্যাপ্লিকেশন ", স্ট্রিং পরিবর্তনশীল "ফোল্ডারে" -র মান ছিল " \ C: \ অ্যাপ্লিকেশন \ application.jar " এবং আমি সমস্যার জন্য পরীক্ষা ছিল পথের নির্ভুলতা
File test = new File(folder);
if(file.isDirectory() && file.canRead()) { //always false }
সুতরাং আমি "পরীক্ষা" সংজ্ঞায়িত করার চেষ্টা করেছি:
String fold= new File(folder).getParentFile().getPath()
File test = new File(fold);
মত "একটি অধিকার বিন্যাসে পথ পেতে : \ অ্যাপ্লিকেশন গ পরিবর্তে" এর " \ C: \ অ্যাপ্লিকেশন \ application.jar " এবং আমি লক্ষ্য করেছি যে এটা কাজ করে।
জার চালানোর সময় সবচেয়ে সহজ সমাধানটি আর্গুমেন্ট হিসাবে পাস করা।
আপনি এটিকে শেল স্ক্রিপ্ট (উইন্ডোজে .bat, .sh যে কোনও জায়গায়) দিয়ে স্বয়ংক্রিয় করতে পারেন:
java -jar my-jar.jar .
আমি .
বর্তমান ওয়ার্কিং ডিরেক্টরিটি পাস করতাম ।
হালনাগাদ
আপনি কোনও সাব-ডিরেক্টরিতে জার ফাইলটি আটকে রাখতে চাইতে পারেন যাতে ব্যবহারকারীরা দুর্ঘটনাক্রমে এটি ক্লিক না করে। আপনার কোডটিতে কমান্ড লাইন আর্গুমেন্ট সরবরাহ করা হয়েছে কিনা তা নিশ্চিত করতে এবং আর্গুমেন্টগুলি অনুপস্থিত থাকলে একটি ভাল ত্রুটির বার্তা সরবরাহ করা উচিত।
অবশেষে একটি কার্যকারী (এবং সংক্ষিপ্ত) সমাধান খুঁজে পাওয়ার আগে আমাকে অনেকটা গোলমাল করতে হয়েছিল।
এটা সম্ভবত jarLocation
একটি উপসর্গ সঙ্গে আসে file:\
বা jar:file\
ব্যবহার করে মুছে ফেলা যেতে পারে, যা String#substring()
।
URL jarLocationUrl = MyClass.class.getProtectionDomain().getCodeSource().getLocation();
String jarLocation = new File(jarLocationUrl.toString()).getParent();
String path = getClass().getResource("").getPath();
পাথ সর্বদা জার ফাইলের মধ্যে থাকা সংস্থানটিকে বোঝায়।
String path = new File(getClass().getResource("").getPath()).getParentFile().getParent(); File jarDir = new File(path.substring(5));
getResource("")
এবং getResource(".")
আমার পরীক্ষায় ব্যর্থ হয়েছিল, যখন ক্লাসটি একটি জেআর ফাইলের মধ্যে থাকতে পারে; উভয় আহ্বান বাতিল।
NullPointerException
।
public static String dir() throws URISyntaxException
{
URI path=Main.class.getProtectionDomain().getCodeSource().getLocation().toURI();
String name= Main.class.getPackage().getName()+".jar";
String path2 = path.getRawPath();
path2=path2.substring(1);
if (path2.contains(".jar"))
{
path2=path2.replace(name, "");
}
return path2;}
উইন্ডোজ ভাল কাজ করে
হতাশাজনক কিছু হ'ল আপনি যখন গ্রহপদে বিকাশ করছেন MyClass.class.getProtectionDomain().getCodeSource().getLocation()
তখন /bin
ডিরেক্টরিটি দুর্দান্ত যা আপনি ফিরে আসেন তবে আপনি যখন এটি একটি জারে সংকলন করেন তখন সেই পথটিতে সেই /myjarname.jar
অংশটি অন্তর্ভুক্ত থাকে যা আপনাকে অবৈধ ফাইলের নাম দেয়।
কোডটি উভয়ই আদর্শে কাজ করতে এবং একবার এটি কোনও জারে সংকলিত হয়ে গেলে, আমি নিম্নলিখিত কোডের টুকরোটি ব্যবহার করি:
URL applicationRootPathURL = getClass().getProtectionDomain().getCodeSource().getLocation();
File applicationRootPath = new File(applicationRootPathURL.getPath());
File myFile;
if(applicationRootPath.isDirectory()){
myFile = new File(applicationRootPath, "filename");
}
else{
myFile = new File(applicationRootPath.getParentFile(), "filename");
}
অন্যদের সম্পর্কে সত্যই নিশ্চিত নয় তবে আমার ক্ষেত্রে এটি একটি "রান্নেবল জার" দিয়ে কাজ করেনি এবং আমি এই লিচ থেকে phchen2 উত্তর এবং অন্যটি থেকে একসাথে কোডগুলি ঠিক করে কাজ করতে পেরেছি: চলমান জেআর ফাইলের পথ কীভাবে পাব? কোড:
String path=new java.io.File(Server.class.getProtectionDomain()
.getCodeSource()
.getLocation()
.getPath())
.getAbsolutePath();
path=path.substring(0, path.lastIndexOf("."));
path=path+System.getProperty("java.class.path");
সেখানে বেশ কয়েকটি সমাধানের চেষ্টা করেছেন কিন্তু কোনওটিই (সম্ভবত বিশেষ) ক্ষেত্রে সঠিক ফলাফল লাভ করতে পারেনি যে সঞ্চালনযোগ্য জারটি ইক্লিপসে "প্যাকেজিং বহিরাগত লাইব্রেরি" দিয়ে রফতানি করা হয়েছে। কোনও কারণে প্রোটেকশনডোমাইন ভিত্তিক সমস্ত সমাধানের ক্ষেত্রে সেই ক্ষেত্রে শূন্য হয়।
উপরের কয়েকটি সমাধানের সংমিশ্রণ থেকে আমি নিম্নলিখিত কার্যকরী কোডটি অর্জন করতে সক্ষম হয়েছি:
String surroundingJar = null;
// gets the path to the jar file if it exists; or the "bin" directory if calling from Eclipse
String jarDir = new File(ClassLoader.getSystemClassLoader().getResource(".").getPath()).getAbsolutePath();
// gets the "bin" directory if calling from eclipse or the name of the .jar file alone (without its path)
String jarFileFromSys = System.getProperty("java.class.path").split(";")[0];
// If both are equal that means it is running from an IDE like Eclipse
if (jarFileFromSys.equals(jarDir))
{
System.out.println("RUNNING FROM IDE!");
// The path to the jar is the "bin" directory in that case because there is no actual .jar file.
surroundingJar = jarDir;
}
else
{
// Combining the path and the name of the .jar file to achieve the final result
surroundingJar = jarDir + jarFileFromSys.substring(1);
}
System.out.println("JAR File: " + surroundingJar);
সংরক্ষণাগারের কোড থেকে কল করা এই পদ্ধতিটি .jar ফাইলটি যেখানে ফোল্ডারে ফিরে আসে। এটি উইন্ডোজ বা ইউনিক্স উভয় ক্ষেত্রেই কাজ করা উচিত।
private String getJarFolder() {
String name = this.getClass().getName().replace('.', '/');
String s = this.getClass().getResource("/" + name + ".class").toString();
s = s.replace('/', File.separatorChar);
s = s.substring(0, s.indexOf(".jar")+4);
s = s.substring(s.lastIndexOf(':')-1);
return s.substring(0, s.lastIndexOf(File.separatorChar)+1);
}
কোড থেকে প্রাপ্ত: জেআর থেকে চলমান কিনা তা নির্ধারণ করুন
উল্লেখ করুন যে এটি কেবলমাত্র চেক করা আছে Windows
তবে আমি মনে করি এটি অন্যান্য অপারেটিং সিস্টেমগুলিতে নির্ভুল কাজ করে [ Linux,MacOs,Solaris
] :)।
একই ডিরেক্টরিতে আমার 2 টি .jar
ফাইল ছিল । আমি এক .jar
ফাইল থেকে অন্য .jar
ফাইলটি একই ডিরেক্টরিতে থাকা অন্য ফাইলটি শুরু করতে চেয়েছিলাম ।
সমস্যাটি হ'ল আপনি যখন cmd
এটি বর্তমান ডিরেক্টরি থেকে শুরু করেন তা হয় system32
।
সতর্কবাণী!
;][[;'57f2g34g87-8+9-09!2#@!$%^^&()
বা এমনকি আমি সমস্ত পরীক্ষাগুলিতে বেশ ভালভাবে কাজ করেছি()%&$%^@#
এটি ভালভাবে কাজ করে।ProcessBuilder
নীচের সাথে নীচের সাথে ব্যবহার করছি :🍂 ..
//The class from which i called this was the class `Main`
String path = getBasePathForClass(Main.class);
String applicationPath= new File(path + "application.jar").getAbsolutePath();
System.out.println("Directory Path is : "+applicationPath);
//Your know try catch here
//Mention that sometimes it doesn't work for example with folder `;][[;'57f2g34g87-8+9-09!2#@!$%^^&()`
ProcessBuilder builder = new ProcessBuilder("java", "-jar", applicationPath);
builder.redirectErrorStream(true);
Process process = builder.start();
//...code
🍂 getBasePathForClass(Class<?> classs)
:
/**
* Returns the absolute path of the current directory in which the given
* class
* file is.
*
* @param classs
* @return The absolute path of the current directory in which the class
* file is.
* @author GOXR3PLUS[StackOverFlow user] + bachden [StackOverFlow user]
*/
public static final String getBasePathForClass(Class<?> classs) {
// Local variables
File file;
String basePath = "";
boolean failed = false;
// Let's give a first try
try {
file = new File(classs.getProtectionDomain().getCodeSource().getLocation().toURI().getPath());
if (file.isFile() || file.getPath().endsWith(".jar") || file.getPath().endsWith(".zip")) {
basePath = file.getParent();
} else {
basePath = file.getPath();
}
} catch (URISyntaxException ex) {
failed = true;
Logger.getLogger(classs.getName()).log(Level.WARNING,
"Cannot firgue out base path for class with way (1): ", ex);
}
// The above failed?
if (failed) {
try {
file = new File(classs.getClassLoader().getResource("").toURI().getPath());
basePath = file.getAbsolutePath();
// the below is for testing purposes...
// starts with File.separator?
// String l = local.replaceFirst("[" + File.separator +
// "/\\\\]", "")
} catch (URISyntaxException ex) {
Logger.getLogger(classs.getName()).log(Level.WARNING,
"Cannot firgue out base path for class with way (2): ", ex);
}
}
// fix to run inside eclipse
if (basePath.endsWith(File.separator + "lib") || basePath.endsWith(File.separator + "bin")
|| basePath.endsWith("bin" + File.separator) || basePath.endsWith("lib" + File.separator)) {
basePath = basePath.substring(0, basePath.length() - 4);
}
// fix to run inside netbeans
if (basePath.endsWith(File.separator + "build" + File.separator + "classes")) {
basePath = basePath.substring(0, basePath.length() - 14);
}
// end fix
if (!basePath.endsWith(File.separator)) {
basePath = basePath + File.separator;
}
return basePath;
}
এই কোডটি আমার পক্ষে কাজ করেছে:
private static String getJarPath() throws IOException, URISyntaxException {
File f = new File(LicensingApp.class.getProtectionDomain().().getLocation().toURI());
String jarPath = f.getCanonicalPath().toString();
String jarDir = jarPath.substring( 0, jarPath.lastIndexOf( File.separator ));
return jarDir;
}
এই কোডটি প্রোগ্রামটি কোনও জেআর ফাইল বা আইডিই-র মধ্যে কার্যকর করা হচ্ছে কিনা তা সনাক্ত করার জন্য আমার পক্ষে কাজ করেছিল:
private static boolean isRunningOverJar() {
try {
String pathJar = Application.class.getResource(Application.class.getSimpleName() + ".class").getFile();
if (pathJar.toLowerCase().contains(".jar")) {
return true;
} else {
return false;
}
} catch (Exception e) {
return false;
}
}
আমার যদি জেআর ফাইলের উইন্ডোজ পূর্ণ পাথের দরকার হয় তবে আমি এই পদ্ধতিটি ব্যবহার করছি:
private static String getPathJar() {
try {
final URI jarUriPath =
Application.class.getResource(Application.class.getSimpleName() + ".class").toURI();
String jarStringPath = jarUriPath.toString().replace("jar:", "");
String jarCleanPath = Paths.get(new URI(jarStringPath)).toString();
if (jarCleanPath.toLowerCase().contains(".jar")) {
return jarCleanPath.substring(0, jarCleanPath.lastIndexOf(".jar") + 4);
} else {
return null;
}
} catch (Exception e) {
log.error("Error getting JAR path.", e);
return null;
}
}
প্রয়োগটি ব্যবহার করে স্প্রিং বুট অ্যাপ্লিকেশনটির সাথে কাজ করা আমার সম্পূর্ণ কোডটি CommandLineRunner
সর্বদা কনসোল ভিউয়ের মধ্যে প্রয়োগটি কার্যকর করা হবে তা নিশ্চিত করতে (জেআর ফাইলের নামে ভুল করে ডাবল ক্লিক), আমি পরবর্তী কোডটি ব্যবহার করছি:
@SpringBootApplication
public class Application implements CommandLineRunner {
public static void main(String[] args) throws IOException {
Console console = System.console();
if (console == null && !GraphicsEnvironment.isHeadless() && isRunningOverJar()) {
Runtime.getRuntime().exec(new String[]{"cmd", "/c", "start", "cmd", "/k",
"java -jar \"" + getPathJar() + "\""});
} else {
SpringApplication.run(Application.class, args);
}
}
@Override
public void run(String... args) {
/*
Additional code here...
*/
}
private static boolean isRunningOverJar() {
try {
String pathJar = Application.class.getResource(Application.class.getSimpleName() + ".class").getFile();
if (pathJar.toLowerCase().contains(".jar")) {
return true;
} else {
return false;
}
} catch (Exception e) {
return false;
}
}
private static String getPathJar() {
try {
final URI jarUriPath =
Application.class.getResource(Application.class.getSimpleName() + ".class").toURI();
String jarStringPath = jarUriPath.toString().replace("jar:", "");
String jarCleanPath = Paths.get(new URI(jarStringPath)).toString();
if (jarCleanPath.toLowerCase().contains(".jar")) {
return jarCleanPath.substring(0, jarCleanPath.lastIndexOf(".jar") + 4);
} else {
return null;
}
} catch (Exception e) {
return null;
}
}
}
আমি জাভা 7 তে লিখি, এবং ওরাকলের রানটাইম সহ উইন্ডোজ 7 এবং ওপেন সোর্স রানটাইম সহ উবুন্টুতে পরীক্ষা করি। এটি সেই সিস্টেমগুলির জন্য নিখুঁতভাবে কাজ করে:
যে কোনও চলমান জার ফাইলের পিতামহ নির্দেশকের পথ (এই কোডটি কল করে এমন শ্রেণি ধরে নেওয়া জার সংরক্ষণাগার নিজেই সরাসরি শিশু child):
try {
fooDir = new File(this.getClass().getClassLoader().getResource("").toURI());
} catch (URISyntaxException e) {
//may be sloppy, but don't really need anything here
}
fooDirPath = fooDir.toString(); // converts abstract (absolute) path to a String
সুতরাং, foo.jar এর পথটি হ'ল:
fooPath = fooDirPath + File.separator + "foo.jar";
আবার কোনও ম্যাক বা পুরানো উইন্ডোজে এটি পরীক্ষা করা হয়নি
getProtectionDomain
পদ্ধতির মাঝে মাঝে কাজ নাও করতে পারে যেমন আপনি কোর জাভা ক্লাস কিছু বয়াম খুঁজে বের করতে হবে যখন (যেমন আমার ক্ষেত্রে StringBuilder
আইবিএম JDK মধ্যে বর্গ), তবে নিম্নলিখিত কাজ অঙ্গীভূতভাবে:
public static void main(String[] args) {
System.out.println(findSource(MyClass.class));
// OR
System.out.println(findSource(String.class));
}
public static String findSource(Class<?> clazz) {
String resourceToSearch = '/' + clazz.getName().replace(".", "/") + ".class";
java.net.URL location = clazz.getResource(resourceToSearch);
String sourcePath = location.getPath();
// Optional, Remove junk
return sourcePath.replace("file:", "").replace("!" + resourceToSearch, "");
}
আমার কাছে ক্লাসের স্ট্রিং অবস্থান পাওয়ার আরও একটি উপায় রয়েছে।
URL path = Thread.currentThread().getContextClassLoader().getResource("");
Path p = Paths.get(path.toURI());
String location = p.toString();
আউটপুট স্ট্রিংয়ের রূপটি থাকবে
C:\Users\Administrator\new Workspace\...
স্পেস এবং অন্যান্য অক্ষরগুলি পরিচালনা করা হয় এবং বিনা আকারে file:/
। সুতরাং ব্যবহার করা সহজ হবে।