Who wants to SCUBA pre-OOW08?

I’m thinking of organizing a 2-tank (or more) scuba dive down in Monterrey, California, a little ways south of SF for the weekend prior to OOW 08. You can’t really scuba in San Francisco Bay–not much there, murky, ships, etc. In Monterrey, it’s a whole different story and there are many dive operators and charters … Continue reading “Who wants to SCUBA pre-OOW08?”

I’m thinking of organizing a 2-tank (or more) scuba dive down in Monterrey, California, a little ways south of SF for the weekend prior to OOW 08. You can’t really scuba in San Francisco Bay–not much there, murky, ships, etc. In Monterrey, it’s a whole different story and there are many dive operators and charters servicing the area. I’m proposing that we dive on Saturday, September 20 (my birthday!)–2 or maybe 3 tanks. For those like me that live in landlocked areas, getting to dive with the sea lions and wildlife of northern California is a rare opportunity.

If there’s enough interest, I’ll coordinate a group and find a charter that will take us out and a shop that will rent all the gear (if you don’t want to lug your own). If there are enough of us, I’ll even figure out a way to transport us from the SF area down to Monterrey and back. At this point, I haven’t made plans, just seeing how much interest there might be. I’ll figure out costs once I figure out how big the group may be.

If you’re interested, comment on this posting and/or email me directly (dannorris@dannorris.com) and I’ll keep a little list of who’s interested. If you’re not attending OOW, but can make it to Monterrey for a dive, you’re welcome too–I just need a dive buddy and I don’t particularly care if they know anything about Oracle :). See you underwater (hopefully)!

Configuring Weblogic For Restart After Reboot on Windows

I have been working on a customer project involving new installations of Oracle Database (a two-node failover cluster using Oracle Clusterware–good stuff) and two load-balanced BEA Oracle Weblogic servers for the middle tier. The middle tier environment runs on Windows Server 2003 Enterprise x64 Edition and is managed by an outsourced hosting facility. I had … Continue reading “Configuring Weblogic For Restart After Reboot on Windows”

I have been working on a customer project involving new installations of Oracle Database (a two-node failover cluster using Oracle Clusterware–good stuff) and two load-balanced BEA Oracle Weblogic servers for the middle tier. The middle tier environment runs on Windows Server 2003 Enterprise x64 Edition and is managed by an outsourced hosting facility.

I had worked with Weblogic before this project, but not on Windows and I was a little surprised by the difficulty finding relatively simple information on BEA’s support site as well as in their documentation.

<rant>I have to say that I’m pleased that Oracle closed this deal so that (I never thought I’d say this) they can make BEA’s support as good as Oracle Support and Metalink. I know it will take quite a while–probably 6-12 months–but it absolutely needs to happen. It’s little reminders like these that make me glad I work with Oracle (or the companies they ultimately buy) and not other software. I’m as guilty as anyone of not knowing how good we Oracle professionals have it when it comes to good, well-organized documentation, a solid support site with a killer knowledge repository (with an awesome search), and a warm, active community of users (too many “thanks to” to mention at this point).</rant>

Back to the reason you’re reading: this post will summarize what turns out to be the relatively easy changes required to ensure that your Windows-based Weblogic managed servers will start up at boot time.

When creating a new Weblogic Domain on Windows, you’ll sometimes have the opportunity to choose the Sun JDK or BEA JRockit JDK to use for your domain’s Java engine. Be conscious of which one you choose (for WL 10.0, it’s on the screen where you choose a Development or Production configuration). I chose BEA JRockit for my environment’s servers because on 64-bit Windows, it’s the only one supported. For 32-bit Windows, you have the option to use Sun’s JDK, but then we’d have a mix and more potential for new bugs to pop up due to the JDK differences. There’s a small change in this process when using Sun’s JDK versus BEA JRockit and I’ll note that as well.

To ensure that your Windows-based BEA Weblogic Managed Server(s) start at boot time, follow these steps:

  1. After creating the new domain and the new Managed Server (Managed Server is a Weblogic term to identify the differences between an Admin Server and the application server where applications should be deployed), modify the Managed Server settings.
  2. Lock & Edit the configuration and proceed to Environment > Servers > (name of your Managed Server) > Configuration tab > Server Start subtab. Then scroll down to the Arguments box and enter -Xnohup in the box. If you’re using Sun’s JDK instead of BEA JRockit, enter -Xrs in that box instead. This is documented at http://edocs.bea.com/wls/docs100/server_start/nodemgr.html#wp1101004.
  3. Once that’s in place, you can Activate Changes.
  4. The admin server says that no restarts are needed, but I would restart it just to make sure. I’m not sure how the admin server can change a JDK flag without restarting the application server. Maybe I’m just not knowledgeable enough to know how it works, but I think it’s just not smart enough to know that you *do* have to restart.
  5. The last change was the one that I missed initially. Briefly, the reason I missed it was that it has to do with crash recovery and in my opinion, a server reboot shouldn’t cause an application server to crash, so I ignored this part of the documentation. One has to ask why you wouldn’t want crash recovery enabled by default anyway, but that’s probably for another rant some other day. Anyway, the final change is to modify a property for the node manager process. Edit BEA_HOME\wlserver_10.0\common\nodemanager\nodemanager.properties and set CrashRecoveryEnabled=true (it is in the file set to false by default). Save and exit the editor.
  6. This is Windows, so go to the Services control panel and restart the BEA Products NodeManager service to put the change into effect.
  7. Ensure that your managed server is up and running. Then, test the changes you’ve made by rebooting the node and see that your managed server restarts after the reboot is complete (and you’ve given time for node manager to start the managed server).

If you have problems, check the node manager logfile (BEA_HOME\wlserver_10.0\common\nodemanager\nodemanager.log) as it will be most useful in determining what happened. If you don’t see any hint that it even tried to restart the server after the reboot, then it’s probably because the crash recovery setting is not enabled–make sure you changed the right thing in the right file.

I didn’t test to see if this process will restart the admin server as well, but I think it probably will or at least should. With a production configuration, you have to enter the username/password for the admin server when starting it, so you may have to store that in the admin server configuration, but that should be a relatively easy fix. In my case, we didn’t want our admin server running all the time and only start it when needed, so having it start after a reboot wasn’t necessary or desired.

Future Oracle events

This is a quick note about upcoming major events on my Oracle event calendar. June 15-19, ODTUG Kaleidoscope 2008, New Orleans, LA September 21-25, Oracle OpenWorld, San Francisco, CA December 1-5, UKOUG Conference, Birmingham, UK February, 2009 (TBD), RMOUG Training Days, Denver, CO March 8-12, 2009, Hotsos Symposium, Dallas, TX April 20-24, 2009, RSA Conference, … Continue reading “Future Oracle events”

This is a quick note about upcoming major events on my Oracle event calendar.

In between these events (hopefully, I’ll get to attend and/or participate in all of them), I’ll also be planning to present at some regional user group events in Charlotte (CLTOUG), Chicago (COUG), Northern California (NoCOUG) and others as time allows.

If you’re going to be at any of these events, please get in touch so we can meet up there. I’m hoping to make more time this year for attending these events and be a little less involved in them so that I can make more time for talking with individuals and/or customers. Hope to see you in the next year at one or more of these venues!

PIPELINED PL/SQL function performance

I recently had an opportunity to do a deeper dive into a performance issue related to the performance of a PIPELINED function. The results weren’t quite what I had expected, so I thought they may be of general interest. As with many performance issues, the issues encountered here are likely data- and database-specific. This was … Continue reading “PIPELINED PL/SQL function performance”

I recently had an opportunity to do a deeper dive into a performance issue related to the performance of a PIPELINED function. The results weren’t quite what I had expected, so I thought they may be of general interest. As with many performance issues, the issues encountered here are likely data- and database-specific. This was testing performed on 10.2.0.3 64-bit non-RAC on Solaris 9.

The PIPELINED function was called like this:

select * from TABLE(pkg1.f1(arg1,arg2,arg3));

And pkg1 is defined like this:

CREATE OR REPLACE PACKAGE pkg1 AS
TYPE coll_table IS TABLE OF custom_persistent_obj_type;
FUNCTION f1 (
p1        IN   NUMBER,
p2             IN   NUMBER,
p3        IN   NUMBER
) RETURN coll_table PIPELINED;
END;
/

The function pkg1.f1 returns a collection of object types, is a little more than 1400 lines long, and contains more than 10 distinct, separate queries, each of them significantly complex involving at least 2 tables, many of them with multiple levels of subqueries. Anyhoo, my chore was to open the idea bin and see if there were some possible enhancements that hadn’t been considered yet.

While reviewing overall performance metrics for the instance, I noted that the DBMS_PICKLER package appeared in the top 10 resource-intensive SQL statements on a regular basis. More digging identified this package as being the primary workhorse behind the TABLE function. So, then the test was clear. Let’s see what happens if we remove PIPELINED, remove TABLE and call the function in a more conventional way. So, my version of the pkg.f would create a collection, add records to it throughout the function’s execution, then return the whole collection at the end with a RETURN statement. The calling function would then need to process this collection into some form to make it more usable by the calling application (similar to the functionality that TABLE provides). For this task, I wrote a stand alone function called DAN.

The new package, pkg2, is defined like this:

CREATE OR REPLACE PACKAGE pkg2 AS
  TYPE coll_table IS TABLE OF custom_persistent_obj_type;
  FUNCTION f2 (
    p1        IN   NUMBER,
    p2             IN   NUMBER,
    p3        IN   NUMBER
  )  RETURN coll_table;
END;
/

DAN is defined as:

CREATE OR REPLACE FUNCTION dan (p_b_tab  IN  pkg2.coll_table,
    p_delimiter     IN  VARCHAR2 DEFAULT ',')
  RETURN VARCHAR2 IS
    l_string     VARCHAR2(32767);
  BEGIN
    for i in p_b_tab.FIRST .. p_b_tab.LAST LOOP
      l_string := l_string || to_char(p_b_tab(i).id1)  ||p_delimiter
                           ||         p_b_tab(i).id2   ||p_delimiter
                           || to_char(p_b_tab(i).array_id)   ||p_delimiter
                           ||         p_b_tab(i).value
      ;
    END LOOP;
  RETURN l_string;
END dan;
/

So, my new units would be called like this:

DECLARE
  l_string      VARCHAR2(32767);
BEGIN
  l_string := dan(pkg2.f2(arg1,arg2,arg3));
  DBMS_OUTPUT.PUT_LINE(l_string);
END;
/

Of course, performance is our primary objective in this case, so timing these two examples side-by-side is the primary chore. I was satisfied that they performed equivalent work and provided equivalent results using different methods. The calling program (custom java, in this case) would have to be modified to handle the changes required, but that may be worth it depending on the time difference.

So, I devised a script to do some very rough testing. The script looked like this:

set timing on echo on termout on pages 0 lines 450 feedb on serveroutput on size 100000
select * from table(pkg1.f1(1095482041,60983,1));
DECLARE
  l_string      VARCHAR2(32767);
BEGIN
  l_string := dan(pkg2.f2(1095482041,60983,1));
  DBMS_OUTPUT.PUT_LINE(l_string);
END;
/

The results were somewhat surprising. Keep in mind that all I’m changing is the way in which data is returned and processed from the function. The data returned, though in slightly different formats, is exactly the same and is not filtered further after it is returned (so there’s no benefit in having it available to run SQL against it).

SELECT (sec) PL/SQL (sec) Difference (sec) Percent Improvement
0.15 0.09 0.06 40.00%
0.14 0.09 0.05 35.71%
0.14 0.10 0.04 28.57%
0.16 0.09 0.07 43.75%
0.15 0.09 0.06 40.00%
0.14 0.12 0.02 14.29%
0.18 0.12 0.06 33.33%
0.18 0.10 0.08 44.44%
0.25 0.12 0.13 52.00%
0.14 0.10 0.04 28.57%
0.18 0.10 0.08 44.44%
0.15 0.10 0.05 33.33%
0.17 0.10 0.07 41.18%
0.18 0.10 0.08 44.44%
0.14 0.10 0.04 28.57%
0.17 0.11 0.06 35.29%
0.17 0.10 0.07 41.18%
0.16 0.10 0.06 37.01% Average
0.14 0.09 0.02 14.29% Min
0.25 0.12 0.13 52.00% Max
8.84% Standard Deviation

As you can see, the results are pretty clear that there is a performance improvement in this case when we avoid using PIPELINED functions. I will also say that the result set from the function body is only about 30 rows. From my review of common uses for PIPELINED functions, it appears that larger collections (result sets) may benefit more from PIPELINED functions as they can likely take more advantage of the parallelism allowed with PIPELINED functions.

2:30am will never happen on Sunday morning

For those that didn’t bother to install the OS, Oracle or other DST patches (to handle the adjusted DST change schedule) last year and elected to just change the time on your servers by hand twice a year, get ready to do that again this weekend. Personally, I’d rather burn two whole regular work days … Continue reading “2:30am will never happen on Sunday morning”

For those that didn’t bother to install the OS, Oracle or other DST patches (to handle the adjusted DST change schedule) last year and elected to just change the time on your servers by hand twice a year, get ready to do that again this weekend. Personally, I’d rather burn two whole regular work days figuring out and installing the patches than get up to modify the time on a server at 2am on Sunday morning, but that’s just me I guess.

For those that forgot the crontab rule about not scheduling things to occur between 1am and 3am (because they either get skipped or run twice once a year), prepare to be confused as 2:30am doesn’t ever happen on clocks in most US states/regions (here are the exceptions).

I’ll look forward to a little more daylight during the hours that count and one hour less sleep on Saturday night.

On a side note, let’s hope that this little posting will get me started on regular posting here…at least for a while!

Cool thing happened on Twitter today…

A neat thing happened today on Twitter. While I admit that I don’t necessarily “get it” as fast as some of my “web 2.0” friends do, I haven’t seen this happen too much on Twitter since I’ve been following it in the past several months. I’m sure it probably happens all the time to cool … Continue reading “Cool thing happened on Twitter today…”

A neat thing happened today on Twitter. While I admit that I don’t necessarily “get it” as fast as some of my “web 2.0” friends do, I haven’t seen this happen too much on Twitter since I’ve been following it in the past several months. I’m sure it probably happens all the time to cool people, but I was lucky enough to cross over for a few minutes and that’s notable.

Basically, the “thing” was that someone needed help understanding how to get started with an OID installation for managing TNS connect descriptors. He wanted (and needed) to use an existing database since he was resource-constrained and wasn’t sure what the installation process looks like for such an installation.

Here’s the combined thread between @fuadar, @topperge and me (@dannorris) just a few minutes ago:

fuadar: looking for someone or some document to install oid in an existing 10.2 database need only names service resolution
dannorris: @fudar It’s much easier to just have it install its own DB. If you use existing DB, you must run metadata repos creation asst first.
fuadar: @dnanorris out of space already have a database out there for other functions. trying to setup oid to solve our tnsnames issues
dannorris: @fudar Issues? Honestly, OID usually introduces more issues than it solves when it comes to TNS. It’s a lot more complex than a text file.
fuadar: @dannorris true but i’m trying to come up with some way to manage acouple of hundred servers and a couple of thousand clients
dannorris: @fudar It’s definitely the right direction to head–just need realistic expectations about complexity and manageability–not easier!
fuadar: @dannorris agree just looking for better documentation
topperge: @fuadar fudar, all you need is RepCA and install the identity repos, http://tinyurl.com/yweyr8
dannorris: @fuadar Better free up some space first–you’ll need a gig or two I’d expect. (ps sorry for misspelling your handle)
fuadar: @topperge so what you are saying is just go thru the oid software install process and then so the repca manually
fuadar: @topperge i am using the Oracle Identity management dvd’s 10.1.4.0.1
dannorris: @fuadar Install RepCA first, run it, then install OID from IdM and tell it to use the repos you created.
dannorris: @fuadar be sure to check DB prereqs (version, pkgs, options, etc.). Follow section here http://snurl.com/1xzda
fuadar: @dannorris thanks reinstalling the software now
topperge: @fuadar There is a 10.1.4 MRCA with the DVDs, install from that first , then install from the OIM Infrastructure CD second
topperge: @fuadar then make sure you patch to 10.1.4.2 which is patch 5983637 on metalink (doing the same install right now)

Even patch numbers! Posting that same question to a forum would likely have taken several hours to get responses–and precise responses as well. Now, I don’t want everyone to believe that @topperge (Matt Topper) and I sit around all day looking for questions we can answer on Twitter. However, I am on Twitter most of the time (even though I don’t tweet that often) and occasionally will throw a response or post in when I think of it. Matt is usually there and seems to behave similarly most of the time.

The bottom line: today, Twitter helped someone solve a real technical problem much faster than they were likely to solve it via other means (web 2 dot oh or otherwise). I don’t know that it happens every day, but we can only save one life at a time :).

You can follow me (@dannorris) on twitter, but as I don’t say much, you won’t likely be impressed. After all, I’m no Jake Kuramoto.

The User Group Conferences Are Coming!

Okay, not for a while, but for those that are presenters at the conference, the US winter is a time of solemn writing. Whitepaper deadlines are approaching for the IOUG program at the Collaborate 08 (April 14-18 in Denver) conference quickly. Soon after, the presentations for those sessions will be due. No rest for the … Continue reading “The User Group Conferences Are Coming!”

Okay, not for a while, but for those that are presenters at the conference, the US winter is a time of solemn writing. Whitepaper deadlines are approaching for the IOUG program at the Collaborate 08 (April 14-18 in Denver) conference quickly. Soon after, the presentations for those sessions will be due. No rest for the wicked after that since ODTUG‘s Kaleidoscope 08 conference will come soon after, in June in New Orleans (note to self: bring extra sweat rags).

As has been the case for several years, the IOUG and ODTUG have graciously selected some of my submissions for presentation at their respective conferences. While ODTUG has announced that they’ve selected their sessions, they haven’t yet posted them or notified many of the speakers.

For the 5 or so people that probably read this blog :), here are the sessions where you’ll find me at Collaborate 08 this year: Continue reading “The User Group Conferences Are Coming!”

Interesting Metalink findings

I generally don’t spend a lot of time surfing around Metalink. Normally, I get in, find the bug or patch or whatever thing I need, and get out. However, my current project involves a database upgrade for a very performance-sensitive application (they have an SLA that they actually have to honor–or honour for my UK … Continue reading “Interesting Metalink findings”

I generally don’t spend a lot of time surfing around Metalink. Normally, I get in, find the bug or patch or whatever thing I need, and get out. However, my current project involves a database upgrade for a very performance-sensitive application (they have an SLA that they actually have to honor–or honour for my UK friends :), so I’ve been doing a bit of research. Coincidentally, a posting to Oracle-L recently allowed me to mention one of my research findings and several subscribers (one publicly) there responded that they had never seen the document and that it was great. Well, it really is great and Oracle Support or whomever it is that supplied the content deserves a great round of applause for putting it together.

The document of which I speak is the Oracle 10g Upgrade Companion. This document contains more than just the upgrade steps, but starts with a list of recommended patches, then goes on to include sections on Behavior Changes (this is especially valuable and absent from most other upgrade plans), Best Practices for the upgrade process, and Documentation references. While I am reporting that this is a great resource, I have two general suggestions for improvement Continue reading “Interesting Metalink findings”

Reflections on OOW 2007

As I think back to last week, there are a few (okay, maybe more than a few) specific things that come to mind, but not in any particular order. Larry‘s laugh during his hour-long monologue on Sunday night Meeting Jake from oracleappslab.com Meeting Eddie Awad Seeing Mark Rittman again Meeting Michael Armstrong-Smith Chance meeting of … Continue reading “Reflections on OOW 2007”

As I think back to last week, there are a few (okay, maybe more than a few) specific things that come to mind, but not in any particular order.

  • Larry‘s laugh during his hour-long monologue on Sunday night
  • Meeting Jake from oracleappslab.com
  • Meeting Eddie Awad
  • Seeing Mark Rittman again
  • Meeting Michael Armstrong-Smith
  • Chance meeting of Morgens Norgaard and Anjo Kolk
  • Seeing Michael Mesaros from Oracle’s IdM Product Management team again
  • Seeing Mike Schrock from F5 again
  • Spending lots of time with Matt Topper
  • Doing a co-presentation with Matt Topper
  • Playing the “Oracle Conclave” sketch from Saturday Night Live on the big screen in one of the session rooms before a presentation
  • Talking with the product manager for Oracle Adaptive Access Manager (OAAM) in the Demogrounds
  • Meeting Rey Ong…twice!
  • Meeting David Kemp in person
  • Seeing friends from IT Convergence, some that are still working there, some that have moved on
  • Chatting with Dan Morgan about his upcoming training offerings
  • Having a lot of people show up at my HA Options For Oracle DB session on Sunday
  • Seeing quite a few people at my RAC For Beginners session on Monday afternoon despite attempts by Oracle to hide me in the last room at the end of the last hallway at the Hilton
  • Having great attendance at the RAC SIG events on Sunday, Monday and Tuesday
  • Seeing the RAC SIG board again
  • Meeting with the IOUG team for dinner and for business
  • Seeing En Vogue (they still look good!), Billy Joel (for a little while), and Lenny Kravitz on Wednesday night
  • Learning how Twitter works and why I should care
  • Meeting with Debbie M again to talk about future opportunities
  • Chatting with my buddies at good ol’ TUSC
  • Meeting Andrew Clarke, Tim Hall, skirt 2.0 wearing Billy Cripe, Rich from oracleappslab.com, Justin Kestelyn, Emily Yip, Vikki Lira, Laurent Schneider, Kutsal Berberoglu, and Chris Muir, to name a few
  • Chatting with Arup Nanda, Jeremy Simmons, Eric Broughton, Matt Vranicar, Eric Camplin, Eric Noelke, Bill Callahan, Jake Van der Vort, Lisa Cowles, Stephanie Trailer, Frank Ryan, Christine Scano
  • Seeing Shaun O’Brien in his new job and uniform
  • Cheering on Piocon as they win their first Titan award (look for another next year :).

These are just some of the things I remember. I have to say that I also attended more sessions this year than I have for the last 2 years combined and learned quite a few interesting things. However, I found the people much more interesting than anything I learned and made some connections that I expect to last far into the future. This was definitely the “people” year for me and the coming year should be very exciting!

There’s a first time for everything

As even long-term parking at O’Hare is expensive, I elected to arrange a car from/to home for OpenWorld last week. I’ve used the same service several times and they’ve always been professional and on time–except this time. The ride from home to the airport was boring enough–they were only 5 minutes late to my door, … Continue reading “There’s a first time for everything”

As even long-term parking at O’Hare is expensive, I elected to arrange a car from/to home for OpenWorld last week. I’ve used the same service several times and they’ve always been professional and on time–except this time.

The ride from home to the airport was boring enough–they were only 5 minutes late to my door, but that’s excusable. The ride home from O’Hare was the more interesting story. As usual at O’Hare, the cars have to wait about 20 minutes from the terminal in a lot. I got off the plane, called to let them know I’m ready and he told me 20 minutes–no surprise. I didn’t time them, but it was about 20 minutes, so that was okay. The negatives began when I sat behind the driver (who was shorter than I am) and got kneecapped as I sat down because his seat was so far back. Turns out, apparently his vehicle (which I presume is exclusively used for chauffeuring people around) has no trunk release, so in order to stow my bag, he had to turn the car off and remove the key from the ignition (how could he not have a spare key?) which in many luxury cars will cause the seat to move all the way back. Now, you’d think that a professional driver would be smart enough to disable this kneecapping feature so that the passenger behind the driver wouldn’t be inconvenienced–I know I would, but then again I guess I am a detail-oriented person.

We finally left the airport with me and one other passenger and headed into rush-hour traffic on Friday evening. It was evident that I was in for a rough ride as the driver had more of a “cab driver” style of flooring the car for every 5-foot advancement and then slamming on the brakes just before ramming into the car ahead. No collisions on this ride, though there were at least two times I had to brace myself on the back of the seat to keep from injuring myself.

The punchline of this joke is that about 3 miles after we left the airport, he pulls off at the O’Hare oasis and mumbled something about gasoline. He drives into the gas station and stops in front of a pump. Turns off the car (which kneecaps me again), hops out of the car and jogs inside the building. I commented to the passenger next to me that this is a first. Seems to me that a professional driver wouldn’t inconvenience his patrons with a stop for gas when he clearly could have done the stop before picking us up. Also, it was rush hour, so the ride was already longer than normal due to traffic. He finally emerges from the station with a cup of coffee in hand and *then* starts to pump the gas. I think the car (a Lincoln Continental) only took about 10 gallons which means it was still about 1/2 full and he just wanted coffee. The rest of the ride home was a jostling ride in traffic where we went 50 mph for 100 feet and then slammed on the brakes again.

I just looked at my receipt and see that I had a little trouble writing my first number, so I will have to confirm that they didn’t interpret that as an 8 instead of a 5 (I intended to give $0 tip). I’m not interested in publicly blackballing this company, but I surely won’t use them again as there are plenty of others ready to take my $$ and I’m not sure it is possible to provide worse service.