How to find specific values in a String?

3

I have to get the Ethernet + IPV4 adapter from Windows, so everything is quiet. I ran the process and stored everything in a String Buffer and sent it back:

public String IP (String tarefa)
{           
    StringBuffer buffer = new StringBuffer();

    try {
        Process processo = Runtime.getRuntime().exec(tarefa);
        InputStream fluxo = processo.getInputStream();
        InputStreamReader lefluxo = new InputStreamReader(fluxo);

        BufferedReader bufferLeitura = new BufferedReader(lefluxo);
        String linha = bufferLeitura.readLine();

        while(linha != null)
        {
            buffer.append(linha);
            buffer.append("\n");                                
            linha = bufferLeitura.readLine();
        }
    } catch (IOException e){
        e.printStackTrace();
    }

    return buffer.toString();
}

Now, I have to get only the network adapter and the IP number to present as a result and I can not think of a way to do such a thing.

How do I split the String into the parts I want? What if you can do this in Main ?

    
asked by anonymous 24.08.2015 / 13:36

1 answer

2

I'm considering that you're running ipconfig , for this case. On my machine when running your code this was the return of your code:

Windows IP Configuration


Ethernet adapter VirtualBox:

   Connection-specific DNS Suffix  . : 
   Link-local IPv6 Address . . . . . : fe80::bd60:54a2:6750:bd19%17
   Autoconfiguration IPv4 Address. . : 169.254.189.25
   Subnet Mask . . . . . . . . . . . : 255.255.0.0
   Default Gateway . . . . . . . . . : 

Ethernet adapter Ethernet:

   Connection-specific DNS Suffix  . : 
   Link-local IPv6 Address . . . . . : fe80::582:c128:49ba:f141%2
   IPv4 Address. . . . . . . . . . . : 192.168.1.100
   Subnet Mask . . . . . . . . . . . : 255.255.255.0
   Default Gateway . . . . . . . . . : 192.168.1.1

Ethernet adapter Bluetooth Network Connection:

   Media State . . . . . . . . . . . : Media disconnected
   Connection-specific DNS Suffix  . : 

Tunnel adapter isatap.{D19E2903-0FED-491B-A030-6B12CB30F3C3}:

   Media State . . . . . . . . . . . : Media disconnected
   Connection-specific DNS Suffix  . : 

Tunnel adapter Teredo Tunneling Pseudo-Interface:

   Connection-specific DNS Suffix  . : 
   IPv6 Address. . . . . . . . . . . : 2001:0:5ef5:79fd:2cd2:ee13:42fb:b44b
   Link-local IPv6 Address . . . . . : fe80::2cd2:ee13:42fb:b44b%19
   Default Gateway . . . . . . . . . : ::

Tunnel adapter isatap.{0D84F8B4-2DA0-4513-9AF4-700EDF9BA40F}:

   Media State . . . . . . . . . . . : Media disconnected
   Connection-specific DNS Suffix  . : 

One way, as already mentioned, is to use regular expressions. In this case I'll need to use two:

  • one to find the adapter, considering lines starting with Ethernet adapter , something like this:
(Ethernet adapter )(\w*)
  • and another to retrieve the IP itself, considering those with IPv4 Address , something like this:
(IPv4 Address)(\. |\: )*(((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(\.|$)){4})

I created an entity just to make it easier to mount the return, I named it NetworkInfo and it looks like this:

public class NetworkInfo {

    private String ip;
    private String adapter;

    // getters e setter

    @Override
    public String toString() {
        return String.format("Adapter: %s | IP: %s", this.getAdapter(), this.getIp());
    }

}

From the result generated by your IP method, we will now go to the resulting string (the one up there) to search for the content that interests us. To not need to do match on lines with no content I'm disregarding them (% with%). Here is an example of a method that processes the if (linha.trim().length() > 0) generated by String ( IP in my example):

private static final Pattern ADAPTER_PATTERN = Pattern.compile("(Ethernet adapter )(\w*)");
private static final Pattern IPV4_PATTERN = Pattern.compile("(IPv4 Address)(\. |\: )*(((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(\.|$)){4})");

public List<NetworkInfo> listNetworkAdapters(final String task) throws Exception {
    final List<NetworkInfo> result = new ArrayList<>();

    String ip = null;
    String adapter = null;

    final String ipconfig = this.ipconfig(task); // "ipconfig" é o seu método "IP".

    final String[] lines = ipconfig.split("\n");

    for (final String line : lines) {
        if (line.trim().length() > 0) {
            final Matcher adapterMatcher = ADAPTER_PATTERN.matcher(line);
            if (adapterMatcher.find()) {
                adapter = adapterMatcher.group(2); // recuperamos apenas o nome, o 2º grupo da regex
            } else {
                final Matcher ipMatcher = IPV4_PATTERN.matcher(line);
                if (ipMatcher.find()) {
                    ip = ipMatcher.group(3); // aqui recuperamos apenas o IP, o 3º grupo da regex
                }
            }

            if (ip != null && adapter != null) {
                final NetworkInfo info = new NetworkInfo();
                info.setIp(ip);
                info.setAdapter(adapter);
                result.add(info);

                ip = null;
                adapter = null;
            }
        }
    }
    return result;
}

Here, as you can see, I am creating an array for each row returned by dividing ipconfig by line break, String . After this we try to look for the patterns we need and when we have a pair formed, we create a \n and add to the return.

From the information obtained by NetworkInfo above, two ipconfig objects were generated as a return by the NetworkInfo method. Making them look like this:

public static void main(final String[] args) throws Exception {
    final List<NetworkInfo> result = new IPConfig().listNetworkAdapters("ipconfig");
    for (final NetworkInfo info : result) {
        System.out.println(info);
    }
}

The result generated was this:

Adapter: VirtualBox | IP: 169.254.189.25
Adapter: Ethernet | IP: 192.168.1.100

I remember that the example is only considering this return, if your pattern is different, update your question with the result you get.

    
31.08.2015 / 02:31