Redis init from Clojure - clojure

I am trying to connect to a remote Redis server, but am having extreme trouble with figuring out how to set it up. I can telnet into the Redis server perfectly fine. From Redis-cli I can connect to the Redis server fine.
But when I setup Redis as I am below I just get:
ConnectException Connection refused java.net.PlainSocketImpl.socketConnect (PlainSocketImpl.java:-2)
(require clj-redis.client :as redis)
(def db (redis/init :url "redis://0.0.0.0:6379))
I've also tried it without the "redis://" section of the url and got the same results.
Does anyone have an idea of what is going on or things to try? Thanks.

I don't know redis specifically but the 0.0.0.0 ip address in the url looks odd. 0.0.0.0 is a non-routable meta-address used to designate an invalid, unknown or non applicable target. When opening a (server) socket for listening you'd do this to signal that the socket should be bound to all ip addresses on the machine, but as a client it doesn't make sense.
;If your redis server is running locally you should do
(require clj-redis.client :as redis)
(def db (redis/init :url "redis://127.0.0.1:6379"))
; better? probably leave out the default port...
(require clj-redis.client :as redis)
(def db (redis/init :url "redis://localhost"))
;if it's remote change ``127.0.0.1`` to the correct address.

i'm using accession
(def c (accession.core/connection-map {})) ;; {} - default settings
and then
(with-connection c "... redis-cmd")

Related

How can I simulate a request from a custom IP address in Clojure?

I want to send multiple requests to my localhost:3000 server from various clients, and I want to simulate that scenario. I'm using the clj-http library to make a request:
(client/get "http://localhost:3000/")
How do I make the request from an ip address other than 127.0.0.1?
One simple answer is to fire up a linux VM in VirtualBox (either directly or by using Vagrant), then make the request from the VM.
Vagrant is an easy-to-use driver since the config files (i.e. Vagrantfile) is simple text and can be checked into git. You can control the IP address of the VM with a simple entry like
config.vm.network "private_network", ip: "192.168.50.4"
See both the
the general Vagrant docs
and the Getting Start docs
(note that they are in 2 different locations!)
Another option could be to have a simple client as a Docker image (or combination of base image and a custom command) and you can launch them fairly quickly. See this answer for some guidance: https://stackoverflow.com/a/24326540/483566
What exactly are you testing? If it's a unit test, send a request to the handler with the desired IP address in the data structure.
If it's an integration test, spin up a server, and use the java library org.apache.http to hit the end points.
To spin up the server use the once fixture. It looks similar to this
(use-fixtures :once
(fn [tests]
(before stuff) ;start server here
(tests)
(after stuff))) ;shut down server here
This is the org.apache.http documentation. This is the subpage you'll want to look at. Read about setting the Requests. You'll want to set the IP address in the header of a request and then send it. Baeldung shows examples of using org.apache.http in java. which you can translate into Clojure code

Connect a repl to Charles Proxy

I'm trying to debug my networked application to find out a network bug with one of my requests. Instead of using the command line, as the error happens inside a library, I'd rather use Charles Proxy for it.
My problem is that the connection is done by https and it's not visible as the REPL is not going through the proxy. I have tried to add -Dhttp.proxyHost and -Dhttp.proxyPort as parameters to the run/debug config to no avail.
Other applications are running through the proxy correctly.
What options am I missing?
It seems the http client library used by twitter-api doesn't honor the JVM http.proxyHost and http.proxyPort properties.
You could try add :proxy {:host "localhost" :port 8888 :protocol :https} as a named parameter to your twitter-api call.

Best Practice Way to Embed NREPL in Clojure Server

I've just started development of a service in Clojure. I'm a little lost in how to approach server shutdown.
I'm using Clojure 1.5.1. For logging, I'm using Timbre 1.5.3. I want to embed NREPL into my server for hot code deployment.
This is my core.clj file. Core is my main and I'm using the app shell that "lein new app" generates.
(ns extenium.core
(:require [taoensso.timbre :as t]
[clojure.tools.nrepl.server :as nrs])
(:gen-class))
(def nrepl-server)
(defn start-nrepl-server []
(t/info "Starting nrepl server on port 8628")
(alter-var-root #'nrepl-server
(constantly
(nrs/start-server :port 8628)))
(t/info "Started nrepl server"))
(defn stop-nrepl-server []
(t/info "Stopping nrepl server")
(nrs/stop-server nrepl-server)
(t/info "Stopped nrepl server"))
(defn start []
(alter-var-root #'*read-eval*
(constantly
false))
(start-nrepl-server))
(defn stop []
(stop-nrepl-server))
(defn -main [& args]
(start))
When I "lein run" the nrepl-server starts as expected, with info messages going to the Terminal. I then connect with "nrepl" from Emacs. No problem. From Emacs I execute "(extenium.core/stop)". At that point, I get the "Stopping nrepl server" message on Emacs (meaning that stdout was redirected to the client). The connection closes (as expected) and I never see the "Stopped nrepl server" message. Fine.
I look at the Terminal and I don't see the "Stopping..." or "Stopped..." messages. Instead, I get the following exception:
Exception in thread "nREPL-worker-0" java.lang.Error: java.net.SocketException: Socket closed
Ideally, I want the following:
To be able to initiate shutdown from an NREPL client. Gracefully close all NREPL client connections without exception. Shutdown with the logging messages directed towards the Terminal (or eventually, a rotating log file).
For the duration of the NREPL connection, clone the logging output to both the server (Terminal or log) and to the NREPL output.
Capture information about incoming NREPL connections, name them, and log connect and disconnect activity.
Eventually, authenticate incoming NREPL connections.
Even later, authorize them for actions they perform.
Disclaimer: I haven't done this, but it seems interesting.
Per the README, specifically the section "Why nREPL?" you should be able to implement 2 - 4 by implementing your own custom transport, perhaps merely extending one of the out-of-the-box ones.
Stopping the server gracefully may entail extending the socket transport. What you are describing as "graceful shutdown" sounds like implementation of a "Logout" protocol.
Authorizing actions they perform seems less straightforward. It looks like you would need to implement a custom Handler, perhaps again wrapping the default-handler with the authorization code.
Good luck!

ClojureScript Repl Security

We have two machines:
server
client
Server is running Clojure + Ring + ... standard ClojureScript webstack.
Client = some machine running Chorme/Firefox/Safari
Now, suppose Server is running a ClojureScriptRepl connection at port 9000 that Client can connect to to setup the ClojureScriptOne Repl.
This allows the server to control the client behavior in certain ways.
However, does this also allow the client to control the server? I.e. does the very act of running a ClojureScript repl allow the client to compromise/control/execute arbitrary code on the server (as running a Clojure Repl would).
Thanks!
Nope. Only strings are moving to server, and server just prints then as string. Practicly there's no overflow attack possibilities, and succeeding with java virtualmachine is not likely, and if it were possible a ton of software woult be wunerable.

How do I stop jetty server in clojure?

I am writing a web application using ring and clojure. I am using the jetty adapter for the development server and emacs/SLIME for IDE. While wrap-reload does help, run-jetty blocks my slime session and I would like to be able to start/stop it at will without having to run it in a separate terminal session. Ideally, I would like to define a server agent and functions start-server and stop-server that would start/stop the server inside the agent. Is this possible?
I usually have a line in my Ring app that looks like the following:
(defonce server (run-jetty #'my-app {:port 8080 :join? false}))
This prevents locking up the REPL. It also allows me to recompile this file without worrying that my server will get redefined. It also lets you interact at the REPL like so:
user=> (.stop server)
and
user=> (.start server)
The Jetty documentation has some information on graceful shutdown of Jetty. That's probably not enough information but it may get you started.
I haven't started playing with compojure yet, but overall I prefer to work with Tomcat. It's more full-featured; among other things, there is a well-documented API for starting it up and shutting it down, it listens for the shutdown command on a dedicated port; there are ant tasks to do this, and they could of course be called from a Java app as well. I just don't know what kind of magic Compojure does with connecting the REPL to a running instance of the Web container, and if/how automatic class reloading happens... hopefully someone else will be able to provide more information.
12 years later.
VSCode / Calva:
If you are like me starting jetty from the repl inside VSCode / Calva
you have to CTRL-C the server process at the terminal not the REPL.
In fact the server process is bound to the terminal not to the REPL.